From c420a2a6ab4f17733396d7eddacb6c299f6cbb90 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 5 Jul 2025 21:54:20 +0800 Subject: [PATCH 001/105] remove unused expressions --- src/main/scala/wasm/StagedMiniWasm.scala | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/main/scala/wasm/StagedMiniWasm.scala b/src/main/scala/wasm/StagedMiniWasm.scala index 2e22e7a71..bfa2082d1 100644 --- a/src/main/scala/wasm/StagedMiniWasm.scala +++ b/src/main/scala/wasm/StagedMiniWasm.scala @@ -433,10 +433,10 @@ trait StagedWasmEvaluator extends SAIOps { def push(v: StagedNum)(implicit ctx: Context): Context = { v match { - case I32(v) => NumType(I32Type); "stack-push".reflectCtrlWith[Unit](v) - case I64(v) => NumType(I64Type); "stack-push".reflectCtrlWith[Unit](v) - case F32(v) => NumType(F32Type); "stack-push".reflectCtrlWith[Unit](v) - case F64(v) => NumType(F64Type); "stack-push".reflectCtrlWith[Unit](v) + case I32(v) => "stack-push".reflectCtrlWith[Unit](v) + case I64(v) => "stack-push".reflectCtrlWith[Unit](v) + case F32(v) => "stack-push".reflectCtrlWith[Unit](v) + case F64(v) => "stack-push".reflectCtrlWith[Unit](v) } ctx.push(v.tipe) } From fb2a2c4e203fba7f571b3142ed2f739e6a7ed5ad Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 7 Jul 2025 14:31:16 +0800 Subject: [PATCH 002/105] let's start from the staged miniwasm interpreter --- .../scala/wasm/StagedConcolicMiniWasm.scala | 1170 +++++++++++++++++ 1 file changed, 1170 insertions(+) create mode 100644 src/main/scala/wasm/StagedConcolicMiniWasm.scala diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala new file mode 100644 index 000000000..6b14bcf61 --- /dev/null +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -0,0 +1,1170 @@ +package gensym.wasm.stagedconcolicminiwasm + +import scala.collection.mutable.{ArrayBuffer, HashMap} + +import lms.core.stub.Adapter +import lms.core.virtualize +import lms.macros.SourceContext +import lms.core.stub.{Base, ScalaGenBase, CGenBase} +import lms.core.Backend._ +import lms.core.Backend.{Block => LMSBlock, Const => LMSConst} +import lms.core.Graph + +import gensym.wasm.ast._ +import gensym.wasm.ast.{Const => WasmConst, Block => WasmBlock} +import gensym.wasm.miniwasm.{ModuleInstance} +import gensym.wasm.ast.{Const => WasmConst, Block => WasmBlock} +import gensym.lmsx.{SAIDriver, StringOps, SAIOps, SAICodeGenBase, CppSAIDriver, CppSAICodeGenBase} + +@virtualize +trait StagedWasmEvaluator extends SAIOps { + def module: ModuleInstance + + trait ReturnSite + + trait StagedNum { + def tipe: ValueType = this match { + case I32(_) => NumType(I32Type) + case I64(_) => NumType(I64Type) + case F32(_) => NumType(F32Type) + case F64(_) => NumType(F64Type) + } + + def i: Rep[Num] + } + case class I32(i: Rep[Num]) extends StagedNum + case class I64(i: Rep[Num]) extends StagedNum + case class F32(i: Rep[Num]) extends StagedNum + case class F64(i: Rep[Num]) extends StagedNum + + implicit def toStagedNum(num: Num): StagedNum = { + num match { + case I32V(_) => I32(num) + case I64V(_) => I64(num) + case F32V(_) => F32(num) + case F64V(_) => F64(num) + } + } + + implicit class ValueTypeOps(ty: ValueType) { + def size: Int = ty match { + case NumType(I32Type) => 4 + case NumType(I64Type) => 8 + case NumType(F32Type) => 4 + case NumType(F64Type) => 8 + } + } + + case class Context( + stackTypes: List[ValueType], + frameTypes: List[ValueType] + ) { + def push(ty: ValueType): Context = { + Context(ty :: stackTypes, frameTypes) + } + + def pop(): (ValueType, Context) = { + val (ty :: rest) = stackTypes + (ty, Context(rest, frameTypes)) + } + + def shift(offset: Int, size: Int): Context = { + // Predef.println(s"[DEBUG] Shifting stack by $offset, size $size, $this") + Predef.assert(offset >= 0, s"Context shift offset must be non-negative, get $offset") + if (offset == 0) { + this + } else { + this.copy( + stackTypes = stackTypes.take(size) ++ stackTypes.drop(offset + size) + ) + } + } + } + + type MCont[A] = Unit => A + type Cont[A] = (MCont[A]) => A + type Trail[A] = List[Context => Rep[Cont[A]]] + + // a cache storing the compiled code for each function, to reduce re-compilation + val compileCache = new HashMap[Int, Rep[(MCont[Unit]) => Unit]] + + def makeDummy: Rep[Unit] = "dummy".reflectCtrlWith[Unit]() + + def funHere[A:Manifest,B:Manifest](f: Rep[A] => Rep[B], dummy: Rep[Unit]): Rep[A => B] = { + // to avoid LMS lifting a function, we create a dummy node and read it inside function + fun((x: Rep[A]) => { + "dummy-op".reflectCtrlWith[Unit](dummy) + f(x) + }) + } + + + def eval(insts: List[Instr], + kont: Context => Rep[Cont[Unit]], + mkont: Rep[MCont[Unit]], + trail: Trail[Unit]) + (implicit ctx: Context): Rep[Unit] = { + if (insts.isEmpty) return kont(ctx)(mkont) + + // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") + // Predef.println(s"[DEBUG] Current context: $ctx") + + val (inst, rest) = (insts.head, insts.tail) + inst match { + case Drop => + val (_, newCtx) = Stack.pop() + eval(rest, kont, mkont, trail)(newCtx) + case WasmConst(num) => + val newCtx = Stack.push(num) + eval(rest, kont, mkont, trail)(newCtx) + case LocalGet(i) => + val newCtx = Stack.push(Frames.get(i)) + eval(rest, kont, mkont, trail)(newCtx) + case LocalSet(i) => + val (num, newCtx) = Stack.pop() + Frames.set(i, num)(newCtx) + eval(rest, kont, mkont, trail)(newCtx) + case LocalTee(i) => + val (num, newCtx) = Stack.peek + Frames.set(i, num) + eval(rest, kont, mkont, trail)(newCtx) + case GlobalGet(i) => + val newCtx = Stack.push(Globals(i)) + eval(rest, kont, mkont, trail)(newCtx) + case GlobalSet(i) => + val (value, newCtx) = Stack.pop() + module.globals(i).ty match { + case GlobalType(tipe, true) => Globals(i) = value + case _ => throw new Exception("Cannot set immutable global") + } + eval(rest, kont, mkont, trail)(newCtx) + case Store(StoreOp(align, offset, ty, None)) => + val (value, newCtx1) = Stack.pop() + val (addr, newCtx2) = Stack.pop()(newCtx1) + Memory.storeInt(addr.toInt, offset, value.toInt) + eval(rest, kont, mkont, trail)(newCtx2) + case Nop => eval(rest, kont, mkont, trail) + case Load(LoadOp(align, offset, ty, None, None)) => + val (addr, newCtx1) = Stack.pop() + val value = Memory.loadInt(addr.toInt, offset) + val newCtx2 = Stack.push(Values.I32V(value))(newCtx1) + eval(rest, kont, mkont, trail)(newCtx2) + case MemorySize => ??? + case MemoryGrow => + val (delta, newCtx1) = Stack.pop() + val newCtx2 = Stack.push(Values.I32V(Memory.grow(delta.toInt)))(newCtx1) + eval(rest, kont, mkont, trail)(newCtx2) + case MemoryFill => ??? + case Unreachable => unreachable() + case Test(op) => + val (v, newCtx1) = Stack.pop() + val newCtx2 = Stack.push(evalTestOp(op, v))(newCtx1) + eval(rest, kont, mkont, trail)(newCtx2) + case Unary(op) => + val (v, newCtx1) = Stack.pop() + val newCtx2 = Stack.push(evalUnaryOp(op, v))(newCtx1) + eval(rest, kont, mkont, trail)(newCtx2) + case Binary(op) => + val (v2, newCtx1) = Stack.pop() + val (v1, newCtx2) = Stack.pop()(newCtx1) + val newCtx3 = Stack.push(evalBinOp(op, v1, v2))(newCtx2) + eval(rest, kont, mkont, trail)(newCtx3) + case Compare(op) => + val (v2, newCtx1) = Stack.pop() + val (v1, newCtx2) = Stack.pop()(newCtx1) + val newCtx3 = Stack.push(evalRelOp(op, v1, v2))(newCtx2) + eval(rest, kont, mkont, trail)(newCtx3) + case WasmBlock(ty, inner) => + // no need to modify the stack when entering a block + // the type system guarantees that we will never take more than the input size from the stack + val funcTy = ty.funcType + val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val dummy = makeDummy + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the block, stackSize =", Stack.size) + val offset = restCtx.stackTypes.size - exitSize + val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) + eval(rest, kont, mk, trail)(newRestCtx) + }) + eval(inner, restK _, mkont, restK _ :: trail) + case Loop(ty, inner) => + val funcTy = ty.funcType + val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val dummy = makeDummy + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the loop, stackSize =", Stack.size) + val offset = restCtx.stackTypes.size - exitSize + val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) + eval(rest, kont, mk, trail)(newRestCtx) + }) + val enterSize = ctx.stackTypes.size + def loop(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Entered the loop, stackSize =", Stack.size) + val offset = restCtx.stackTypes.size - enterSize + val newRestCtx = Stack.shift(offset, funcTy.inps.size)(restCtx) + eval(inner, restK _, mk, loop _ :: trail)(newRestCtx) + }) + loop(ctx)(mkont) + case If(ty, thn, els) => + val funcTy = ty.funcType + val (cond, newCtx) = Stack.pop() + val exitSize = newCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size + // TODO: can we avoid code duplication here? + val dummy = makeDummy + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the if, stackSize =", Stack.size) + val offset = restCtx.stackTypes.size - exitSize + val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) + eval(rest, kont, mk, trail)(newRestCtx) + }) + if (cond.toInt != 0) { + eval(thn, restK _, mkont, restK _ :: trail)(newCtx) + } else { + eval(els, restK _, mkont, restK _ :: trail)(newCtx) + } + () + case Br(label) => + info(s"Jump to $label") + trail(label)(ctx)(mkont) + case BrIf(label) => + val (cond, newCtx) = Stack.pop() + info(s"The br_if(${label})'s condition is ", cond.toInt) + if (cond.toInt != 0) { + info(s"Jump to $label") + trail(label)(newCtx)(mkont) + } else { + info(s"Continue") + eval(rest, kont, mkont, trail)(newCtx) + } + () + case BrTable(labels, default) => + val (cond, newCtx) = Stack.pop() + def aux(choices: List[Int], idx: Int): Rep[Unit] = { + if (choices.isEmpty) trail(default)(newCtx)(mkont) + else { + if (cond.toInt == idx) trail(choices.head)(newCtx)(mkont) + else aux(choices.tail, idx + 1) + } + } + aux(labels, 0) + case Return => trail.last(ctx)(mkont) + case Call(f) => evalCall(rest, kont, mkont, trail, f, false) + case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) + case _ => + val todo = "todo-op".reflectCtrlWith[Unit]() + eval(rest, kont, mkont, trail) + } + } + + def forwardKont: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => mk(())) + + + def evalCall(rest: List[Instr], + kont: Context => Rep[Cont[Unit]], + mkont: Rep[MCont[Unit]], + trail: Trail[Unit], + funcIndex: Int, + isTail: Boolean) + (implicit ctx: Context): Rep[Unit] = { + module.funcs(funcIndex) match { + case FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) => + val locals = bodyLocals ++ ty.inps + val callee = + if (compileCache.contains(funcIndex)) { + compileCache(funcIndex) + } else { + val callee = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Entered the function at $funcIndex, stackSize =", Stack.size) + // we can do some check here to ensure the function returns correct size of stack + eval(body, (_: Context) => forwardKont, mk, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) + }) + compileCache(funcIndex) = callee + callee + } + // Predef.println(s"[DEBUG] locals size: ${locals.size}") + val (args, newCtx) = Stack.take(ty.inps.size) + if (isTail) { + // when tail call, return to the caller's return continuation + Frames.popFrame(ctx.frameTypes.size) + Frames.pushFrame(locals) + Frames.putAll(args) + callee(mkont) + } else { + // We make a new trail by `restK`, since function creates a new block to escape + // (more or less like `return`) + val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + Frames.popFrame(locals.size) + eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) + }) + val dummy = makeDummy + val newMKont: Rep[MCont[Unit]] = funHere((_u: Rep[Unit]) => { + restK(mkont) + }, dummy) + Frames.pushFrame(locals) + Frames.putAll(args) + callee(newMKont) + } + case Import("console", "log", _) + | Import("spectest", "print_i32", _) => + //println(s"[DEBUG] current stack: $stack") + val (v, newCtx) = Stack.pop() + println(v.toInt) + eval(rest, kont, mkont, trail)(newCtx) + case Import(_, _, _) => throw new Exception(s"Unknown import at $funcIndex") + case _ => throw new Exception(s"Definition at $funcIndex is not callable") + } + } + + def evalTestOp(op: TestOp, value: StagedNum): StagedNum = op match { + case Eqz(_) => Values.I32V(if (value.toInt == 0) 1 else 0) + } + + def evalUnaryOp(op: UnaryOp, value: StagedNum): StagedNum = op match { + case Clz(_) => value.clz() + case Ctz(_) => value.ctz() + case Popcnt(_) => value.popcnt() + case _ => ??? + } + + def evalBinOp(op: BinOp, v1: StagedNum, v2: StagedNum): StagedNum = op match { + case Add(_) => v1 + v2 + case Mul(_) => v1 * v2 + case Sub(_) => v1 - v2 + case Shl(_) => v1 << v2 + // case ShrS(_) => v1 >> v2 // TODO: signed shift right + case ShrU(_) => v1 >> v2 + case And(_) => v1 & v2 + case DivS(_) => v1 / v2 + case DivU(_) => v1 / v2 + case _ => + throw new Exception(s"Unknown binary operation $op") + } + + def evalRelOp(op: RelOp, v1: StagedNum, v2: StagedNum): StagedNum = op match { + case Eq(_) => v1 numEq v2 + case Ne(_) => v1 numNe v2 + case LtS(_) => v1 < v2 + case LtU(_) => v1 ltu v2 + case GtS(_) => v1 > v2 + case GtU(_) => v1 gtu v2 + case LeS(_) => v1 <= v2 + case LeU(_) => v1 leu v2 + case GeS(_) => v1 >= v2 + case GeU(_) => v1 geu v2 + case _ => ??? + } + + def evalTop(mkont: Rep[MCont[Unit]], main: Option[String]): Rep[Unit] = { + val funBody: FuncBodyDef = main match { + case Some(func_name) => + module.defs.flatMap({ + case Export(`func_name`, ExportFunc(fid)) => + Predef.println(s"Now compiling start with function $main") + module.funcs(fid) match { + case FuncDef(_, body@FuncBodyDef(_,_,_,_)) => Some(body) + case _ => throw new Exception("Entry function has no concrete body") + } + case _ => None + }).head + case None => + val startIds = module.defs.flatMap { + case Start(id) => Some(id) + case _ => None + } + val startId = startIds.headOption.getOrElse { throw new Exception("No start function") } + module.funcs(startId) match { + case FuncDef(_, body@FuncBodyDef(_,_,_,_)) => body + case _ => + throw new Exception("Entry function has no concrete body") + } + } + val (instrs, locals) = (funBody.body, funBody.locals) + Stack.initialize() + Frames.pushFrame(locals) + eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) + Frames.popFrame(locals.size) + } + + def evalTop(main: Option[String], printRes: Boolean = false): Rep[Unit] = { + val haltK: Rep[Unit] => Rep[Unit] = (_) => { + info("Exiting the program...") + if (printRes) { + Stack.print() + } + "no-op".reflectCtrlWith[Unit]() + } + val temp: Rep[MCont[Unit]] = topFun(haltK) + evalTop(temp, main) + } + + // stack operations + object Stack { + def shift(offset: Int, size: Int)(ctx: Context): Context = { + if (offset > 0) { + "stack-shift".reflectCtrlWith[Unit](offset, size) + } + ctx.shift(offset, size) + } + + def initialize(): Rep[Unit] = { + "stack-init".reflectCtrlWith[Unit]() + } + + def pop()(implicit ctx: Context): (StagedNum, Context) = { + val (ty, newContext) = ctx.pop() + val num = ty match { + case NumType(I32Type) => I32("stack-pop".reflectCtrlWith[Num]()) + case NumType(I64Type) => I64("stack-pop".reflectCtrlWith[Num]()) + case NumType(F32Type) => F32("stack-pop".reflectCtrlWith[Num]()) + case NumType(F32Type) => F64("stack-pop".reflectCtrlWith[Num]()) + } + (num, newContext) + } + + def peek(implicit ctx: Context): (StagedNum, Context) = { + val ty = ctx.stackTypes.head + val num = ty match { + case NumType(I32Type) => I32("stack-peek".reflectCtrlWith[Num]()) + case NumType(I64Type) => I64("stack-peek".reflectCtrlWith[Num]()) + case NumType(F32Type) => F32("stack-peek".reflectCtrlWith[Num]()) + case NumType(F32Type) => F64("stack-peek".reflectCtrlWith[Num]()) + } + (num, ctx) + } + + def push(v: StagedNum)(implicit ctx: Context): Context = { + v match { + case I32(v) => "stack-push".reflectCtrlWith[Unit](v) + case I64(v) => "stack-push".reflectCtrlWith[Unit](v) + case F32(v) => "stack-push".reflectCtrlWith[Unit](v) + case F64(v) => "stack-push".reflectCtrlWith[Unit](v) + } + ctx.push(v.tipe) + } + + def take(n: Int)(implicit ctx: Context): (List[StagedNum], Context) = n match { + case 0 => (Nil, ctx) + case n => + val (v, newCtx1) = pop() + val (rest, newCtx2) = take(n - 1) + (v::rest, newCtx2) + } + + def drop(n: Int)(implicit ctx: Context): Context = { + take(n)._2 + } + + def shift(offset: Rep[Int], size: Rep[Int]): Rep[Unit] = { + if (offset > 0) { + "stack-shift".reflectCtrlWith[Unit](offset, size) + } + } + + def print(): Rep[Unit] = { + "stack-print".reflectCtrlWith[Unit]() + } + + def size: Rep[Int] = { + "stack-size".reflectCtrlWith[Int]() + } + } + + object Frames { + def get(i: Int)(implicit ctx: Context): StagedNum = { + // val offset = ctx.frameTypes.take(i).map(_.size).sum + ctx.frameTypes(i) match { + case NumType(I32Type) => I32("frame-get".reflectCtrlWith[Num](i)) + case NumType(I64Type) => I64("frame-get".reflectCtrlWith[Num](i)) + case NumType(F32Type) => F32("frame-get".reflectCtrlWith[Num](i)) + case NumType(F64Type) => F64("frame-get".reflectCtrlWith[Num](i)) + } + } + + def set(i: Int, v: StagedNum)(implicit ctx: Context): Rep[Unit] = { + // val offset = ctx.frameTypes.take(i).map(_.size).sum + v match { + case I32(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case I64(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case F32(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case F64(v) => "frame-set".reflectCtrlWith[Unit](i, v) + } + } + + def pushFrame(locals: List[ValueType]): Rep[Unit] = { + // Predef.println(s"[DEBUG] push frame: $locals") + val size = locals.size + "frame-push".reflectCtrlWith[Unit](size) + } + + def popFrame(size: Int): Rep[Unit] = { + "frame-pop".reflectCtrlWith[Unit](size) + } + + def putAll(args: List[StagedNum])(implicit ctx: Context): Rep[Unit] = { + for ((arg, i) <- args.view.reverse.zipWithIndex) { + Frames.set(i, arg) + } + } + } + + object Memory { + def storeInt(base: Rep[Int], offset: Int, value: Rep[Int]): Rep[Unit] = { + "memory-store-int".reflectCtrlWith[Unit](base, offset, value) + } + + def loadInt(base: Rep[Int], offset: Int): Rep[Int] = { + "memory-load-int".reflectCtrlWith[Int](base, offset) + } + + def grow(delta: Rep[Int]): Rep[Int] = { + "memory-grow".reflectCtrlWith[Int](delta) + } + } + + // call unreachable + def unreachable(): Rep[Unit] = { + "unreachable".reflectCtrlWith[Unit]() + } + + def info(xs: Rep[_]*): Rep[Unit] = { + "info".reflectCtrlWith[Unit](xs: _*) + } + + // runtime values + object Values { + def I32V(i: Rep[Int]): StagedNum = { + I32("I32V".reflectCtrlWith[Num](i)) + } + + def I64V(i: Rep[Long]): StagedNum = { + I64("I64V".reflectCtrlWith[Num](i)) + } + } + + // global read/write + object Globals { + def apply(i: Int): StagedNum = { + module.globals(i).ty match { + case GlobalType(NumType(I32Type), _) => I32("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(I64Type), _) => I64("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(F32Type), _) => F32("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(F64Type), _) => F64("global-get".reflectCtrlWith[Num](i)) + } + } + + def update(i: Int, v: StagedNum): Rep[Unit] = { + module.globals(i).ty match { + case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i) + case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i) + case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i) + case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i) + } + } + } + + // runtime Num type + implicit class StagedNumOps(num: StagedNum) { + + def toInt: Rep[Int] = "num-to-int".reflectCtrlWith[Int](num.i) + + def clz(): StagedNum = num match { + case I32(i) => I32("clz".reflectCtrlWith[Num](i)) + case I64(i) => I64("clz".reflectCtrlWith[Num](i)) + } + + def ctz(): StagedNum = num match { + case I32(i) => I32("ctz".reflectCtrlWith[Num](i)) + case I64(i) => I64("ctz".reflectCtrlWith[Num](i)) + } + + def popcnt(): StagedNum = num match { + case I32(i) => I32("popcnt".reflectCtrlWith[Num](i)) + case I64(i) => I64("popcnt".reflectCtrlWith[Num](i)) + } + + def +(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-add".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-add".reflectCtrlWith[Num](x, y)) + case (F32(x), F32(y)) => F32("binary-add".reflectCtrlWith[Num](x, y)) + case (F64(x), F64(y)) => F64("binary-add".reflectCtrlWith[Num](x, y)) + } + } + + def -(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-sub".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-sub".reflectCtrlWith[Num](x, y)) + case (F32(x), F32(y)) => F32("binary-sub".reflectCtrlWith[Num](x, y)) + case (F64(x), F64(y)) => F64("binary-sub".reflectCtrlWith[Num](x, y)) + } + } + + def *(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-mul".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-mul".reflectCtrlWith[Num](x, y)) + case (F32(x), F32(y)) => F32("binary-mul".reflectCtrlWith[Num](x, y)) + case (F64(x), F64(y)) => F64("binary-mul".reflectCtrlWith[Num](x, y)) + } + } + + def /(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-div".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-div".reflectCtrlWith[Num](x, y)) + case (F32(x), F32(y)) => F32("binary-div".reflectCtrlWith[Num](x, y)) + case (F64(x), F64(y)) => F64("binary-div".reflectCtrlWith[Num](x, y)) + } + } + + def <<(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-shl".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-shl".reflectCtrlWith[Num](x, y)) + } + } + + def >>(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-shr".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-shr".reflectCtrlWith[Num](x, y)) + } + } + + def &(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("binary-and".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I64("binary-and".reflectCtrlWith[Num](x, y)) + } + } + + def numEq(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-eq".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-eq".reflectCtrlWith[Num](x, y)) + } + } + + def numNe(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-ne".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-ne".reflectCtrlWith[Num](x, y)) + } + } + + def <(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-lt".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-lt".reflectCtrlWith[Num](x, y)) + } + } + + def ltu(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-ltu".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-ltu".reflectCtrlWith[Num](x, y)) + } + } + + def >(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-gt".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-gt".reflectCtrlWith[Num](x, y)) + } + } + + def gtu(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-gtu".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-gtu".reflectCtrlWith[Num](x, y)) + } + } + + def <=(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-le".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-le".reflectCtrlWith[Num](x, y)) + } + } + + def leu(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-leu".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-leu".reflectCtrlWith[Num](x, y)) + } + } + + def >=(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-ge".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-ge".reflectCtrlWith[Num](x, y)) + } + } + + def geu(rhs: StagedNum): StagedNum = { + (num, rhs) match { + case (I32(x), I32(y)) => I32("relation-geu".reflectCtrlWith[Num](x, y)) + case (I64(x), I64(y)) => I32("relation-geu".reflectCtrlWith[Num](x, y)) + } + } + } +} + +trait StagedWasmScalaGen extends ScalaGenBase with SAICodeGenBase { + override def mayInline(n: Node): Boolean = n match { + case Node(s, "stack-pop", _, _) => false + case _ => super.mayInline(n) + } + + override def traverse(n: Node): Unit = n match { + case Node(_, "stack-drop", List(n), _) => + emit("Stack.drop("); shallow(n); emit(")\n") + case Node(_, "stack-reset", List(n), _) => + emit("Stack.reset("); shallow(n); emit(")\n") + case Node(_, "stack-init", _, _) => + emit("Stack.initialize()\n") + case Node(_, "stack-print", _, _) => + emit("Stack.print()\n") + case Node(_, "frame-push", List(i), _) => + emit("Frames.pushFrame("); shallow(i); emit(")\n") + case Node(_, "frame-pop", List(i), _) => + emit("Frames.popFrame("); shallow(i); emit(")\n") + case Node(_, "frame-putAll", List(args), _) => + emit("Frames.putAll("); shallow(args); emit(")\n") + case Node(_, "frame-set", List(i, value), _) => + emit("Frames.set("); shallow(i); emit(", "); shallow(value); emit(")\n") + case Node(_, "global-set", List(i, value), _) => + emit("Global.globalSet("); shallow(i); emit(", "); shallow(value); emit(")\n") + case _ => super.traverse(n) + } + + // code generation for pure nodes + override def shallow(n: Node): Unit = n match { + case Node(_, "frame-get", List(i), _) => + emit("Frames.get("); shallow(i); emit(")") + case Node(_, "frame-pop", List(i), _) => + emit("Frames.popFrame("); shallow(i); emit(")") + case Node(_, "stack-push", List(value), _) => + emit("Stack.push("); shallow(value); emit(")") + case Node(_, "stack-pop", _, _) => + emit("Stack.pop()") + case Node(_, "stack-peek", _, _) => + emit("Stack.peek") + case Node(_, "stack-take", List(n), _) => + emit("Stack.take("); shallow(n); emit(")") + case Node(_, "stack-size", _, _) => + emit("Stack.size") + case Node(_, "global-get", List(i), _) => + emit("Global.globalGet("); shallow(i); emit(")") + case Node(_, "binary-add", List(lhs, rhs), _) => + shallow(lhs); emit(" + "); shallow(rhs) + case Node(_, "binary-sub", List(lhs, rhs), _) => + shallow(lhs); emit(" - "); shallow(rhs) + case Node(_, "binary-mul", List(lhs, rhs), _) => + shallow(lhs); emit(" * "); shallow(rhs) + case Node(_, "binary-div", List(lhs, rhs), _) => + shallow(lhs); emit(" / "); shallow(rhs) + case Node(_, "binary-shl", List(lhs, rhs), _) => + shallow(lhs); emit(" << "); shallow(rhs) + case Node(_, "binary-shr", List(lhs, rhs), _) => + shallow(lhs); emit(" >> "); shallow(rhs) + case Node(_, "binary-and", List(lhs, rhs), _) => + shallow(lhs); emit(" & "); shallow(rhs) + case Node(_, "relation-eq", List(lhs, rhs), _) => + shallow(lhs); emit(" == "); shallow(rhs) + case Node(_, "relation-ne", List(lhs, rhs), _) => + shallow(lhs); emit(" != "); shallow(rhs) + case Node(_, "relation-lt", List(lhs, rhs), _) => + shallow(lhs); emit(" < "); shallow(rhs) + case Node(_, "relation-ltu", List(lhs, rhs), _) => + shallow(lhs); emit(" < "); shallow(rhs) + case Node(_, "relation-gt", List(lhs, rhs), _) => + shallow(lhs); emit(" > "); shallow(rhs) + case Node(_, "relation-gtu", List(lhs, rhs), _) => + shallow(lhs); emit(" > "); shallow(rhs) + case Node(_, "relation-le", List(lhs, rhs), _) => + shallow(lhs); emit(" <= "); shallow(rhs) + case Node(_, "relation-leu", List(lhs, rhs), _) => + shallow(lhs); emit(" <= "); shallow(rhs) + case Node(_, "relation-ge", List(lhs, rhs), _) => + shallow(lhs); emit(" >= "); shallow(rhs) + case Node(_, "relation-geu", List(lhs, rhs), _) => + shallow(lhs); emit(" >= "); shallow(rhs) + case Node(_, "num-to-int", List(num), _) => + shallow(num); emit(".toInt") + case Node(_, "no-op", _, _) => + emit("()") + case _ => super.shallow(n) + } +} + +trait WasmToScalaCompilerDriver[A, B] + extends SAIDriver[A, B] with StagedWasmEvaluator { q => + override val codegen = new StagedWasmScalaGen { + val IR: q.type = q + import IR._ + override def remap(m: Manifest[_]): String = { + if (m.toString.endsWith("Stack")) "Stack" + else if(m.toString.endsWith("Frame")) "Frame" + else super.remap(m) + } + } + + override val prelude = + """ +object Prelude { + sealed abstract class Num { + def +(that: Num): Num = (this, that) match { + case (I32V(x), I32V(y)) => I32V(x + y) + case (I64V(x), I64V(y)) => I64V(x + y) + case _ => throw new RuntimeException("Invalid addition") + } + + def -(that: Num): Num = (this, that) match { + case (I32V(x), I32V(y)) => I32V(x - y) + case (I64V(x), I64V(y)) => I64V(x - y) + case _ => throw new RuntimeException("Invalid subtraction") + } + + def !=(that: Num): Num = (this, that) match { + case (I32V(x), I32V(y)) => I32V(if (x != y) 1 else 0) + case (I64V(x), I64V(y)) => I32V(if (x != y) 1 else 0) + case _ => throw new RuntimeException("Invalid inequality") + } + + def toInt: Int = this match { + case I32V(i) => i + case I64V(i) => i.toInt + } + } + case class I32V(i: Int) extends Num + case class I64V(i: Long) extends Num + +object Stack { + private val buffer = new scala.collection.mutable.ArrayBuffer[Num]() + def push(v: Num): Unit = buffer.append(v) + def pop(): Num = { + buffer.remove(buffer.size - 1) + } + def peek: Num = { + buffer.last + } + def size: Int = buffer.size + def drop(n: Int): Unit = { + buffer.remove(buffer.size - n, n) + } + def take(n: Int): List[Num] = { + val xs = buffer.takeRight(n).toList + drop(n) + xs + } + def reset(size: Int): Unit = { + info(s"Reset stack to size $size") + while (buffer.size > size) { + buffer.remove(buffer.size - 1) + } + } + def initialize(): Unit = buffer.clear() + def print(): Unit = { + println("Stack: " + buffer.mkString(", ")) + } +} + + class Frame(val size: Int) { + private val data = new Array[Num](size) + def apply(i: Int): Num = { + info(s"frame(${i}) is ${data(i)}") + data(i) + } + def update(i: Int, v: Num): Unit = { + info(s"set frame(${i}) to ${v}") + data(i) = v + } + def putAll(xs: List[Num]): Unit = { + for (i <- 0 until xs.size) { + data(i) = xs(i) + } + } + override def toString: String = { + "Frame(" + data.mkString(", ") + ")" + } + } + + object Frames { + private var frames = List[Frame]() + def pushFrame(size: Int): Unit = { + frames = new Frame(size) :: frames + } + def popFrame(): Unit = { + frames = frames.tail + } + def top: Frame = frames.head + def set(i: Int, v: Num): Unit = { + top(i) = v + } + def get(i: Int): Num = { + top(i) + } + } + + object Global { + // TODO: create global with specific size + private val globals = new Array[Num](10) + def globalGet(i: Int): Num = globals(i) + def globalSet(i: Int, v: Num): Unit = globals(i) = v + } + + def info(xs: Any*): Unit = { + if (System.getenv("DEBUG") != null) { + println("[INFO] " + xs.mkString(" ")) + } + } +} +import Prelude._ + + +object Main { + def main(args: Array[String]): Unit = { + val snippet = new Snippet() + snippet(()) + } +} +""" +} + + +object WasmToScalaCompiler { + def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean = false): String = { + println(s"Now compiling wasm module with entry function $main") + val code = new WasmToScalaCompilerDriver[Unit, Unit] { + def module: ModuleInstance = moduleInst + def snippet(x: Rep[Unit]): Rep[Unit] = { + evalTop(main, printRes) + } + } + code.code + } +} + +trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { + // clear include path and headers by first + includePaths.clear() + headers.clear() + + registerHeader("headers", "\"wasm.hpp\"") + registerHeader("") + registerHeader("") + registerHeader("") + registerHeader("") + + override def mayInline(n: Node): Boolean = n match { + case Node(_, "stack-pop", _, _) + | Node(_, "stack-peek", _, _) + => false + case _ => super.mayInline(n) + } + + override def remap(m: Manifest[_]): String = { + if (m.toString.endsWith("Num")) "Num" + else if (m.toString.endsWith("Frame")) "Frame" + else if (m.toString.endsWith("Stack")) "Stack" + else if (m.toString.endsWith("Global")) "Global" + else if (m.toString.endsWith("I32V")) "I32V" + else if (m.toString.endsWith("I64V")) "I64V" + else super.remap(m) + } + + // for now, the traverse/shallow is same as the scala backend's + override def traverse(n: Node): Unit = n match { + case Node(_, "stack-push", List(value), _) => + emit("Stack.push("); shallow(value); emit(");\n") + case Node(_, "stack-drop", List(n), _) => + emit("Stack.drop("); shallow(n); emit(");\n") + case Node(_, "stack-init", _, _) => + emit("Stack.initialize();\n") + case Node(_, "stack-print", _, _) => + emit("Stack.print();\n") + case Node(_, "frame-push", List(i), _) => + emit("Frames.pushFrame("); shallow(i); emit(");\n") + case Node(_, "frame-pop", List(i), _) => + emit("Frames.popFrame("); shallow(i); emit(");\n") + case Node(_, "frame-putAll", List(args), _) => + emit("Frames.putAll("); shallow(args); emit(");\n") + case Node(_, "frame-set", List(i, value), _) => + emit("Frames.set("); shallow(i); emit(", "); shallow(value); emit(");\n") + case Node(_, "global-set", List(i, value), _) => + emit("Global.globalSet("); shallow(i); emit(", "); shallow(value); emit(");\n") + // Note: The following code is copied from the traverse of CppBackend.scala, try to avoid duplicated code + case n @ Node(f, "λ", (b: LMSBlock)::LMSConst(0)::rest, _) => + // TODO: Is a leading block followed by 0 a hint for top function? + super.traverse(n) + case n @ Node(f, "λ", (b: LMSBlock)::rest, _) => + val retType = remap(typeBlockRes(b.res)) + val argTypes = b.in.map(a => remap(typeMap(a))).mkString(", ") + emitln(s"std::function<$retType(${argTypes})> ${quote(f)};") + emit(quote(f)); emit(" = ") + quoteTypedBlock(b, false, true, capture = "&") + emitln(";") + case _ => super.traverse(n) + } + + // code generation for pure nodes + override def shallow(n: Node): Unit = n match { + case Node(_, "frame-get", List(i), _) => + emit("Frames.get("); shallow(i); emit(")") + case Node(_, "stack-drop", List(n), _) => + emit("Stack.drop("); shallow(n); emit(")") + case Node(_, "stack-push", List(value), _) => + emit("Stack.push("); shallow(value); emit(")") + case Node(_, "stack-shift", List(offset, size), _) => + emit("Stack.shift("); shallow(offset); emit(", "); shallow(size); emit(")") + case Node(_, "stack-pop", _, _) => + emit("Stack.pop()") + case Node(_, "frame-pop", List(i), _) => + emit("Frames.popFrame("); shallow(i); emit(")") + case Node(_, "stack-peek", _, _) => + emit("Stack.peek()") + case Node(_, "stack-take", List(n), _) => + emit("Stack.take("); shallow(n); emit(")") + case Node(_, "slice-reverse", List(slice), _) => + shallow(slice); emit(".reverse") + case Node(_, "memory-store-int", List(base, offset, value), _) => + emit("Memory.storeInt("); shallow(base); emit(", "); shallow(offset); emit(", "); shallow(value); emit(")") + case Node(_, "memory-load-int", List(base, offset), _) => + emit("Memory.loadInt("); shallow(base); emit(", "); shallow(offset); emit(")") + case Node(_, "memory-grow", List(delta), _) => + emit("Memory.grow("); shallow(delta); emit(")") + case Node(_, "stack-size", _, _) => + emit("Stack.size()") + case Node(_, "global-get", List(i), _) => + emit("Global.globalGet("); shallow(i); emit(")") + case Node(_, "binary-add", List(lhs, rhs), _) => + shallow(lhs); emit(" + "); shallow(rhs) + case Node(_, "binary-sub", List(lhs, rhs), _) => + shallow(lhs); emit(" - "); shallow(rhs) + case Node(_, "binary-mul", List(lhs, rhs), _) => + shallow(lhs); emit(" * "); shallow(rhs) + case Node(_, "binary-div", List(lhs, rhs), _) => + shallow(lhs); emit(" / "); shallow(rhs) + case Node(_, "binary-shl", List(lhs, rhs), _) => + shallow(lhs); emit(" << "); shallow(rhs) + case Node(_, "binary-shr", List(lhs, rhs), _) => + shallow(lhs); emit(" >> "); shallow(rhs) + case Node(_, "binary-and", List(lhs, rhs), _) => + shallow(lhs); emit(" & "); shallow(rhs) + case Node(_, "relation-eq", List(lhs, rhs), _) => + shallow(lhs); emit(" == "); shallow(rhs) + case Node(_, "relation-ne", List(lhs, rhs), _) => + shallow(lhs); emit(" != "); shallow(rhs) + case Node(_, "relation-lt", List(lhs, rhs), _) => + shallow(lhs); emit(" < "); shallow(rhs) + case Node(_, "relation-ltu", List(lhs, rhs), _) => + shallow(lhs); emit(" < "); shallow(rhs) + case Node(_, "relation-gt", List(lhs, rhs), _) => + shallow(lhs); emit(" > "); shallow(rhs) + case Node(_, "relation-gtu", List(lhs, rhs), _) => + shallow(lhs); emit(" > "); shallow(rhs) + case Node(_, "relation-le", List(lhs, rhs), _) => + shallow(lhs); emit(" <= "); shallow(rhs) + case Node(_, "relation-leu", List(lhs, rhs), _) => + shallow(lhs); emit(" <= "); shallow(rhs) + case Node(_, "relation-ge", List(lhs, rhs), _) => + shallow(lhs); emit(" >= "); shallow(rhs) + case Node(_, "relation-geu", List(lhs, rhs), _) => + shallow(lhs); emit(" >= "); shallow(rhs) + case Node(_, "num-to-int", List(num), _) => + shallow(num); emit(".toInt()") + case Node(_, "dummy", _, _) => emit("std::monostate()") + case Node(_, "dummy-op", _, _) => emit("std::monostate()") + case Node(_, "no-op", _, _) => + emit("std::monostate()") + case _ => super.shallow(n) + } + + override def registerTopLevelFunction(id: String, streamId: String = "general")(f: => Unit) = + if (!registeredFunctions(id)) { + //if (ongoingFun(streamId)) ??? + //ongoingFun += streamId + registeredFunctions += id + withStream(functionsStreams.getOrElseUpdate(id, { + val functionsStream = new java.io.ByteArrayOutputStream() + val functionsWriter = new java.io.PrintStream(functionsStream) + (functionsWriter, functionsStream) + })._1)(f) + //ongoingFun -= streamId + } else { + // If a function is registered, don't re-register it. + // withStream(functionsStreams(id)._1)(f) + } + + override def emitAll(g: Graph, name: String)(m1: Manifest[_], m2: Manifest[_]): Unit = { + val ng = init(g) + emitHeaders(stream) + emitln(""" + |/***************************************** + |Emitting Generated Code + |*******************************************/ + """.stripMargin) + val src = run(name, ng) + emitFunctionDecls(stream) + emitDatastructures(stream) + emitFunctions(stream) + emit(src) + emitln(""" + |/***************************************** + |End of Generated Code + |*******************************************/ + |int main(int argc, char *argv[]) { + | Snippet(std::monostate{}); + | return 0; + |}""".stripMargin) + } +} + +trait WasmToCppCompilerDriver[A, B] extends CppSAIDriver[A, B] with StagedWasmEvaluator { q => + override val codegen = new StagedWasmCppGen { + val IR: q.type = q + import IR._ + } +} + +object WasmToCppCompiler { + case class GeneratedCpp(source: String, headerFolders: List[String]) + + def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean = false): GeneratedCpp = { + println(s"Now compiling wasm module with entry function $main") + val driver = new WasmToCppCompilerDriver[Unit, Unit] { + def module: ModuleInstance = moduleInst + def snippet(x: Rep[Unit]): Rep[Unit] = { + evalTop(main, printRes) + } + } + GeneratedCpp(driver.code, driver.codegen.includePaths.toList) + } + + def compileToExe(moduleInst: ModuleInstance, + main: Option[String], + outputCpp: String, + outputExe: String, + printRes: Boolean = false): Unit = { + val generated = compile(moduleInst, main, printRes) + val code = generated.source + + val writer = new java.io.PrintWriter(new java.io.File(outputCpp)) + try { + writer.write(code) + } finally { + writer.close() + } + + import sys.process._ + val command = s"g++ -std=c++17 $outputCpp -o $outputExe -O3 -g " + generated.headerFolders.map(f => s"-I$f").mkString(" ") + if (command.! != 0) { + throw new RuntimeException(s"Compilation failed for $outputCpp") + } + } + +} + From 27e3e32f9269303d21d65583f6b2d14a74b04dbe Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 7 Jul 2025 14:34:24 +0800 Subject: [PATCH 003/105] dup all concrete operations to symbolic --- .../scala/wasm/StagedConcolicMiniWasm.scala | 444 +++++------------- 1 file changed, 111 insertions(+), 333 deletions(-) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 6b14bcf61..22b593a93 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -13,8 +13,9 @@ import lms.core.Graph import gensym.wasm.ast._ import gensym.wasm.ast.{Const => WasmConst, Block => WasmBlock} import gensym.wasm.miniwasm.{ModuleInstance} -import gensym.wasm.ast.{Const => WasmConst, Block => WasmBlock} +import gensym.wasm.symbolic.{SymVal} import gensym.lmsx.{SAIDriver, StringOps, SAIOps, SAICodeGenBase, CppSAIDriver, CppSAICodeGenBase} +import gensym.wasm.symbolic.Concrete @virtualize trait StagedWasmEvaluator extends SAIOps { @@ -24,25 +25,27 @@ trait StagedWasmEvaluator extends SAIOps { trait StagedNum { def tipe: ValueType = this match { - case I32(_) => NumType(I32Type) - case I64(_) => NumType(I64Type) - case F32(_) => NumType(F32Type) - case F64(_) => NumType(F64Type) + case I32(_, _) => NumType(I32Type) + case I64(_, _) => NumType(I64Type) + case F32(_, _) => NumType(F32Type) + case F64(_, _) => NumType(F64Type) } def i: Rep[Num] + + def s: Rep[SymVal] } - case class I32(i: Rep[Num]) extends StagedNum - case class I64(i: Rep[Num]) extends StagedNum - case class F32(i: Rep[Num]) extends StagedNum - case class F64(i: Rep[Num]) extends StagedNum + case class I32(i: Rep[Num], s: Rep[SymVal]) extends StagedNum + case class I64(i: Rep[Num], s: Rep[SymVal]) extends StagedNum + case class F32(i: Rep[Num], s: Rep[SymVal]) extends StagedNum + case class F64(i: Rep[Num], s: Rep[SymVal]) extends StagedNum implicit def toStagedNum(num: Num): StagedNum = { num match { - case I32V(_) => I32(num) - case I64V(_) => I64(num) - case F32V(_) => F32(num) - case F64V(_) => F64(num) + case I32V(_) => I32(num, Concrete(num)) + case I64V(_) => I64(num, Concrete(num)) + case F32V(_) => F32(num, Concrete(num)) + case F64V(_) => F64(num, Concrete(num)) } } @@ -147,7 +150,7 @@ trait StagedWasmEvaluator extends SAIOps { case Load(LoadOp(align, offset, ty, None, None)) => val (addr, newCtx1) = Stack.pop() val value = Memory.loadInt(addr.toInt, offset) - val newCtx2 = Stack.push(Values.I32V(value))(newCtx1) + val newCtx2 = Stack.push(value)(newCtx1) eval(rest, kont, mkont, trail)(newCtx2) case MemorySize => ??? case MemoryGrow => @@ -414,10 +417,10 @@ trait StagedWasmEvaluator extends SAIOps { def pop()(implicit ctx: Context): (StagedNum, Context) = { val (ty, newContext) = ctx.pop() val num = ty match { - case NumType(I32Type) => I32("stack-pop".reflectCtrlWith[Num]()) - case NumType(I64Type) => I64("stack-pop".reflectCtrlWith[Num]()) - case NumType(F32Type) => F32("stack-pop".reflectCtrlWith[Num]()) - case NumType(F32Type) => F64("stack-pop".reflectCtrlWith[Num]()) + case NumType(I32Type) => I32("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(I64Type) => I64("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F32("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F64("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) } (num, newContext) } @@ -425,22 +428,22 @@ trait StagedWasmEvaluator extends SAIOps { def peek(implicit ctx: Context): (StagedNum, Context) = { val ty = ctx.stackTypes.head val num = ty match { - case NumType(I32Type) => I32("stack-peek".reflectCtrlWith[Num]()) - case NumType(I64Type) => I64("stack-peek".reflectCtrlWith[Num]()) - case NumType(F32Type) => F32("stack-peek".reflectCtrlWith[Num]()) - case NumType(F32Type) => F64("stack-peek".reflectCtrlWith[Num]()) + case NumType(I32Type) => I32("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(I64Type) => I64("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F32("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F64("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) } (num, ctx) } - def push(v: StagedNum)(implicit ctx: Context): Context = { - v match { - case I32(v) => "stack-push".reflectCtrlWith[Unit](v) - case I64(v) => "stack-push".reflectCtrlWith[Unit](v) - case F32(v) => "stack-push".reflectCtrlWith[Unit](v) - case F64(v) => "stack-push".reflectCtrlWith[Unit](v) + def push(num: StagedNum)(implicit ctx: Context): Context = { + num match { + case I32(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) + case I64(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) + case F32(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) + case F64(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) } - ctx.push(v.tipe) + ctx.push(num.tipe) } def take(n: Int)(implicit ctx: Context): (List[StagedNum], Context) = n match { @@ -458,6 +461,7 @@ trait StagedWasmEvaluator extends SAIOps { def shift(offset: Rep[Int], size: Rep[Int]): Rep[Unit] = { if (offset > 0) { "stack-shift".reflectCtrlWith[Unit](offset, size) + "sym-stack-shift".reflectCtrlWith[Unit](offset, size) } } @@ -474,20 +478,20 @@ trait StagedWasmEvaluator extends SAIOps { def get(i: Int)(implicit ctx: Context): StagedNum = { // val offset = ctx.frameTypes.take(i).map(_.size).sum ctx.frameTypes(i) match { - case NumType(I32Type) => I32("frame-get".reflectCtrlWith[Num](i)) - case NumType(I64Type) => I64("frame-get".reflectCtrlWith[Num](i)) - case NumType(F32Type) => F32("frame-get".reflectCtrlWith[Num](i)) - case NumType(F64Type) => F64("frame-get".reflectCtrlWith[Num](i)) + case NumType(I32Type) => I32("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(I64Type) => I64("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(F32Type) => F32("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(F64Type) => F64("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) } } def set(i: Int, v: StagedNum)(implicit ctx: Context): Rep[Unit] = { // val offset = ctx.frameTypes.take(i).map(_.size).sum v match { - case I32(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case I64(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case F32(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case F64(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case I32(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) + case I64(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) + case F32(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) + case F64(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) } } @@ -495,10 +499,12 @@ trait StagedWasmEvaluator extends SAIOps { // Predef.println(s"[DEBUG] push frame: $locals") val size = locals.size "frame-push".reflectCtrlWith[Unit](size) + "sym-frame-push".reflectCtrlWith[Unit](size) } def popFrame(size: Int): Rep[Unit] = { "frame-pop".reflectCtrlWith[Unit](size) + "sym-frame-pop".reflectCtrlWith[Unit](size) } def putAll(args: List[StagedNum])(implicit ctx: Context): Rep[Unit] = { @@ -513,8 +519,8 @@ trait StagedWasmEvaluator extends SAIOps { "memory-store-int".reflectCtrlWith[Unit](base, offset, value) } - def loadInt(base: Rep[Int], offset: Int): Rep[Int] = { - "memory-load-int".reflectCtrlWith[Int](base, offset) + def loadInt(base: Rep[Int], offset: Int): StagedNum = { + I32("I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset)), "sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) } def grow(delta: Rep[Int]): Rep[Int] = { @@ -534,11 +540,11 @@ trait StagedWasmEvaluator extends SAIOps { // runtime values object Values { def I32V(i: Rep[Int]): StagedNum = { - I32("I32V".reflectCtrlWith[Num](i)) + I32("I32V".reflectCtrlWith[Num](i), "Concrete".reflectCtrlWith[SymVal]("I32V".reflectCtrlWith[Num](i))) } def I64V(i: Rep[Long]): StagedNum = { - I64("I64V".reflectCtrlWith[Num](i)) + I64("I64V".reflectCtrlWith[Num](i), "Concrete".reflectCtrlWith[SymVal]("I64V".reflectCtrlWith[Num](i))) } } @@ -546,19 +552,19 @@ trait StagedWasmEvaluator extends SAIOps { object Globals { def apply(i: Int): StagedNum = { module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => I32("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(I64Type), _) => I64("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(F32Type), _) => F32("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(F64Type), _) => F64("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(I32Type), _) => I32("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(I64Type), _) => I64("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(F32Type), _) => F32("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(F64Type), _) => F64("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) } } def update(i: Int, v: StagedNum): Rep[Unit] = { module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i) - case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i) - case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i) - case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i) + case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) + case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) + case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) + case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) } } } @@ -569,382 +575,153 @@ trait StagedWasmEvaluator extends SAIOps { def toInt: Rep[Int] = "num-to-int".reflectCtrlWith[Int](num.i) def clz(): StagedNum = num match { - case I32(i) => I32("clz".reflectCtrlWith[Num](i)) - case I64(i) => I64("clz".reflectCtrlWith[Num](i)) + case I32(x_c, x_s) => I32("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) + case I64(x_c, x_s) => I64("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) } def ctz(): StagedNum = num match { - case I32(i) => I32("ctz".reflectCtrlWith[Num](i)) - case I64(i) => I64("ctz".reflectCtrlWith[Num](i)) + case I32(x_c, x_s) => I32("ctz".reflectCtrlWith[Num](x_c), "sym-ctz".reflectCtrlWith[SymVal](x_s)) + case I64(x_c, x_s) => I64("ctz".reflectCtrlWith[Num](x_c), "sym-ctz".reflectCtrlWith[SymVal](x_s)) } def popcnt(): StagedNum = num match { - case I32(i) => I32("popcnt".reflectCtrlWith[Num](i)) - case I64(i) => I64("popcnt".reflectCtrlWith[Num](i)) + case I32(x_c, x_s) => I32("popcnt".reflectCtrlWith[Num](x_c), "sym-popcnt".reflectCtrlWith[SymVal](x_s)) + case I64(x_c, x_s) => I64("popcnt".reflectCtrlWith[Num](x_c), "sym-popcnt".reflectCtrlWith[SymVal](x_s)) } def +(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-add".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-add".reflectCtrlWith[Num](x, y)) - case (F32(x), F32(y)) => F32("binary-add".reflectCtrlWith[Num](x, y)) - case (F64(x), F64(y)) => F64("binary-add".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) } } + def -(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-sub".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-sub".reflectCtrlWith[Num](x, y)) - case (F32(x), F32(y)) => F32("binary-sub".reflectCtrlWith[Num](x, y)) - case (F64(x), F64(y)) => F64("binary-sub".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) } } def *(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-mul".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-mul".reflectCtrlWith[Num](x, y)) - case (F32(x), F32(y)) => F32("binary-mul".reflectCtrlWith[Num](x, y)) - case (F64(x), F64(y)) => F64("binary-mul".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) } } def /(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-div".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-div".reflectCtrlWith[Num](x, y)) - case (F32(x), F32(y)) => F32("binary-div".reflectCtrlWith[Num](x, y)) - case (F64(x), F64(y)) => F64("binary-div".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) } } def <<(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-shl".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-shl".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) } } def >>(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-shr".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-shr".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) } } def &(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("binary-and".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I64("binary-and".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) + case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) + case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) } } def numEq(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-eq".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-eq".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-eq".reflectCtrlWith[Num](x_c, y_c), "sym-relation-eq".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-eq".reflectCtrlWith[Num](x_c, y_c), "sym-relation-eq".reflectCtrlWith[SymVal](x_s, y_s)) } } def numNe(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-ne".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-ne".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ne".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ne".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ne".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ne".reflectCtrlWith[SymVal](x_s, y_s)) } } def <(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-lt".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-lt".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-lt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-lt".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-lt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-lt".reflectCtrlWith[SymVal](x_s, y_s)) } } def ltu(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-ltu".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-ltu".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ltu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ltu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ltu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ltu".reflectCtrlWith[SymVal](x_s, y_s)) } } def >(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-gt".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-gt".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-gt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gt".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-gt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gt".reflectCtrlWith[SymVal](x_s, y_s)) } } def gtu(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-gtu".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-gtu".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-gtu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gtu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-gtu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gtu".reflectCtrlWith[SymVal](x_s, y_s)) } } def <=(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-le".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-le".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-le".reflectCtrlWith[Num](x_c, y_c), "sym-relation-le".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-le".reflectCtrlWith[Num](x_c, y_c), "sym-relation-le".reflectCtrlWith[SymVal](x_s, y_s)) } } def leu(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-leu".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-leu".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-leu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-leu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-leu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-leu".reflectCtrlWith[SymVal](x_s, y_s)) } } def >=(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-ge".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-ge".reflectCtrlWith[Num](x, y)) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ge".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ge".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ge".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ge".reflectCtrlWith[SymVal](x_s, y_s)) } } def geu(rhs: StagedNum): StagedNum = { (num, rhs) match { - case (I32(x), I32(y)) => I32("relation-geu".reflectCtrlWith[Num](x, y)) - case (I64(x), I64(y)) => I32("relation-geu".reflectCtrlWith[Num](x, y)) - } - } - } -} - -trait StagedWasmScalaGen extends ScalaGenBase with SAICodeGenBase { - override def mayInline(n: Node): Boolean = n match { - case Node(s, "stack-pop", _, _) => false - case _ => super.mayInline(n) - } - - override def traverse(n: Node): Unit = n match { - case Node(_, "stack-drop", List(n), _) => - emit("Stack.drop("); shallow(n); emit(")\n") - case Node(_, "stack-reset", List(n), _) => - emit("Stack.reset("); shallow(n); emit(")\n") - case Node(_, "stack-init", _, _) => - emit("Stack.initialize()\n") - case Node(_, "stack-print", _, _) => - emit("Stack.print()\n") - case Node(_, "frame-push", List(i), _) => - emit("Frames.pushFrame("); shallow(i); emit(")\n") - case Node(_, "frame-pop", List(i), _) => - emit("Frames.popFrame("); shallow(i); emit(")\n") - case Node(_, "frame-putAll", List(args), _) => - emit("Frames.putAll("); shallow(args); emit(")\n") - case Node(_, "frame-set", List(i, value), _) => - emit("Frames.set("); shallow(i); emit(", "); shallow(value); emit(")\n") - case Node(_, "global-set", List(i, value), _) => - emit("Global.globalSet("); shallow(i); emit(", "); shallow(value); emit(")\n") - case _ => super.traverse(n) - } - - // code generation for pure nodes - override def shallow(n: Node): Unit = n match { - case Node(_, "frame-get", List(i), _) => - emit("Frames.get("); shallow(i); emit(")") - case Node(_, "frame-pop", List(i), _) => - emit("Frames.popFrame("); shallow(i); emit(")") - case Node(_, "stack-push", List(value), _) => - emit("Stack.push("); shallow(value); emit(")") - case Node(_, "stack-pop", _, _) => - emit("Stack.pop()") - case Node(_, "stack-peek", _, _) => - emit("Stack.peek") - case Node(_, "stack-take", List(n), _) => - emit("Stack.take("); shallow(n); emit(")") - case Node(_, "stack-size", _, _) => - emit("Stack.size") - case Node(_, "global-get", List(i), _) => - emit("Global.globalGet("); shallow(i); emit(")") - case Node(_, "binary-add", List(lhs, rhs), _) => - shallow(lhs); emit(" + "); shallow(rhs) - case Node(_, "binary-sub", List(lhs, rhs), _) => - shallow(lhs); emit(" - "); shallow(rhs) - case Node(_, "binary-mul", List(lhs, rhs), _) => - shallow(lhs); emit(" * "); shallow(rhs) - case Node(_, "binary-div", List(lhs, rhs), _) => - shallow(lhs); emit(" / "); shallow(rhs) - case Node(_, "binary-shl", List(lhs, rhs), _) => - shallow(lhs); emit(" << "); shallow(rhs) - case Node(_, "binary-shr", List(lhs, rhs), _) => - shallow(lhs); emit(" >> "); shallow(rhs) - case Node(_, "binary-and", List(lhs, rhs), _) => - shallow(lhs); emit(" & "); shallow(rhs) - case Node(_, "relation-eq", List(lhs, rhs), _) => - shallow(lhs); emit(" == "); shallow(rhs) - case Node(_, "relation-ne", List(lhs, rhs), _) => - shallow(lhs); emit(" != "); shallow(rhs) - case Node(_, "relation-lt", List(lhs, rhs), _) => - shallow(lhs); emit(" < "); shallow(rhs) - case Node(_, "relation-ltu", List(lhs, rhs), _) => - shallow(lhs); emit(" < "); shallow(rhs) - case Node(_, "relation-gt", List(lhs, rhs), _) => - shallow(lhs); emit(" > "); shallow(rhs) - case Node(_, "relation-gtu", List(lhs, rhs), _) => - shallow(lhs); emit(" > "); shallow(rhs) - case Node(_, "relation-le", List(lhs, rhs), _) => - shallow(lhs); emit(" <= "); shallow(rhs) - case Node(_, "relation-leu", List(lhs, rhs), _) => - shallow(lhs); emit(" <= "); shallow(rhs) - case Node(_, "relation-ge", List(lhs, rhs), _) => - shallow(lhs); emit(" >= "); shallow(rhs) - case Node(_, "relation-geu", List(lhs, rhs), _) => - shallow(lhs); emit(" >= "); shallow(rhs) - case Node(_, "num-to-int", List(num), _) => - shallow(num); emit(".toInt") - case Node(_, "no-op", _, _) => - emit("()") - case _ => super.shallow(n) - } -} - -trait WasmToScalaCompilerDriver[A, B] - extends SAIDriver[A, B] with StagedWasmEvaluator { q => - override val codegen = new StagedWasmScalaGen { - val IR: q.type = q - import IR._ - override def remap(m: Manifest[_]): String = { - if (m.toString.endsWith("Stack")) "Stack" - else if(m.toString.endsWith("Frame")) "Frame" - else super.remap(m) - } - } - - override val prelude = - """ -object Prelude { - sealed abstract class Num { - def +(that: Num): Num = (this, that) match { - case (I32V(x), I32V(y)) => I32V(x + y) - case (I64V(x), I64V(y)) => I64V(x + y) - case _ => throw new RuntimeException("Invalid addition") - } - - def -(that: Num): Num = (this, that) match { - case (I32V(x), I32V(y)) => I32V(x - y) - case (I64V(x), I64V(y)) => I64V(x - y) - case _ => throw new RuntimeException("Invalid subtraction") - } - - def !=(that: Num): Num = (this, that) match { - case (I32V(x), I32V(y)) => I32V(if (x != y) 1 else 0) - case (I64V(x), I64V(y)) => I32V(if (x != y) 1 else 0) - case _ => throw new RuntimeException("Invalid inequality") - } - - def toInt: Int = this match { - case I32V(i) => i - case I64V(i) => i.toInt - } - } - case class I32V(i: Int) extends Num - case class I64V(i: Long) extends Num - -object Stack { - private val buffer = new scala.collection.mutable.ArrayBuffer[Num]() - def push(v: Num): Unit = buffer.append(v) - def pop(): Num = { - buffer.remove(buffer.size - 1) - } - def peek: Num = { - buffer.last - } - def size: Int = buffer.size - def drop(n: Int): Unit = { - buffer.remove(buffer.size - n, n) - } - def take(n: Int): List[Num] = { - val xs = buffer.takeRight(n).toList - drop(n) - xs - } - def reset(size: Int): Unit = { - info(s"Reset stack to size $size") - while (buffer.size > size) { - buffer.remove(buffer.size - 1) - } - } - def initialize(): Unit = buffer.clear() - def print(): Unit = { - println("Stack: " + buffer.mkString(", ")) - } -} - - class Frame(val size: Int) { - private val data = new Array[Num](size) - def apply(i: Int): Num = { - info(s"frame(${i}) is ${data(i)}") - data(i) - } - def update(i: Int, v: Num): Unit = { - info(s"set frame(${i}) to ${v}") - data(i) = v - } - def putAll(xs: List[Num]): Unit = { - for (i <- 0 until xs.size) { - data(i) = xs(i) + case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-geu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-geu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-geu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-geu".reflectCtrlWith[SymVal](x_s, y_s)) } } - override def toString: String = { - "Frame(" + data.mkString(", ") + ")" - } - } - - object Frames { - private var frames = List[Frame]() - def pushFrame(size: Int): Unit = { - frames = new Frame(size) :: frames - } - def popFrame(): Unit = { - frames = frames.tail - } - def top: Frame = frames.head - def set(i: Int, v: Num): Unit = { - top(i) = v - } - def get(i: Int): Num = { - top(i) - } - } - - object Global { - // TODO: create global with specific size - private val globals = new Array[Num](10) - def globalGet(i: Int): Num = globals(i) - def globalSet(i: Int, v: Num): Unit = globals(i) = v - } - - def info(xs: Any*): Unit = { - if (System.getenv("DEBUG") != null) { - println("[INFO] " + xs.mkString(" ")) - } - } -} -import Prelude._ - - -object Main { - def main(args: Array[String]): Unit = { - val snippet = new Snippet() - snippet(()) - } -} -""" -} - - -object WasmToScalaCompiler { - def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean = false): String = { - println(s"Now compiling wasm module with entry function $main") - val code = new WasmToScalaCompilerDriver[Unit, Unit] { - def module: ModuleInstance = moduleInst - def snippet(x: Rep[Unit]): Rep[Unit] = { - evalTop(main, printRes) - } - } - code.code } } @@ -1168,3 +945,4 @@ object WasmToCppCompiler { } + From 2143050a320d3fa182aa361bc6b9c154aff9045d Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 7 Jul 2025 21:46:15 +0800 Subject: [PATCH 004/105] maintain a symbolic stack during the execution --- headers/wasm.hpp | 1 + headers/wasm/concrete_rt.hpp | 7 +- headers/wasm/symbolic_rt.hpp | 72 +++++++++++++++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 52 ++++++++++---- .../genwasym/TestStagedConcolicEval.scala | 33 +++++++++ 5 files changed, 152 insertions(+), 13 deletions(-) create mode 100644 headers/wasm/symbolic_rt.hpp create mode 100644 src/test/scala/genwasym/TestStagedConcolicEval.scala diff --git a/headers/wasm.hpp b/headers/wasm.hpp index 21da2ff75..c7e98b6eb 100644 --- a/headers/wasm.hpp +++ b/headers/wasm.hpp @@ -2,5 +2,6 @@ #define WASM_HEADERS #include "wasm/concrete_rt.hpp" +#include "wasm/symbolic_rt.hpp" #endif \ No newline at end of file diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 34d739f41..e994cbde7 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -1,3 +1,6 @@ +#ifndef WASM_CONCRETE_RT_HPP +#define WASM_CONCRETE_RT_HPP + #include #include #include @@ -200,4 +203,6 @@ struct Memory_t { } }; -static Memory_t Memory(1); // 1 page memory \ No newline at end of file +static Memory_t Memory(1); // 1 page memory + +#endif // WASM_CONCRETE_RT_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp new file mode 100644 index 000000000..d03509acb --- /dev/null +++ b/headers/wasm/symbolic_rt.hpp @@ -0,0 +1,72 @@ +#ifndef WASM_SYMBOLIC_RT_HPP +#define WASM_SYMBOLIC_RT_HPP + +#include "concrete_rt.hpp" +#include + +class SymVal { +public: + SymVal operator+(const SymVal &other) const { + // Define how to add two symbolic values + // Not implemented yet + return SymVal(); + } + + SymVal is_zero() const { + // Check if the symbolic value is zero + // Not implemented yet + return SymVal(); + } +}; + +class SymStack_t { +public: + void push(SymVal val) { + // Push a symbolic value to the stack + // Not implemented yet + } + + SymVal pop() { + // Pop a symbolic value from the stack + // Not implemented yet + return SymVal(); + } + + SymVal peek() { return SymVal(); } +}; + +static SymStack_t SymStack; + +class SymFrames_t { +public: + void pushFrame(int size) { + // Push a new frame with the given size + // Not implemented yet + } + std::monostate popFrame(int size) { + // Pop the frame of the given size + // Not implemented yet + return std::monostate(); + } + + SymVal get(int index) { + // Get the symbolic value at the given index + // Not implemented yet + return SymVal(); + } + + void set(int index, SymVal val) { + // Set the symbolic value at the given index + // Not implemented yet + } +}; + +static SymFrames_t SymFrames; + +static SymVal Concrete(Num num) { + // Convert a concrete number to a symbolic value + // Not implemented yet + return SymVal(); +} + +#endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 22b593a93..c41c7c42f 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -40,7 +40,7 @@ trait StagedWasmEvaluator extends SAIOps { case class F32(i: Rep[Num], s: Rep[SymVal]) extends StagedNum case class F64(i: Rep[Num], s: Rep[SymVal]) extends StagedNum - implicit def toStagedNum(num: Num): StagedNum = { + def toStagedNum(num: Num): StagedNum = { num match { case I32V(_) => I32(num, Concrete(num)) case I64V(_) => I64(num, Concrete(num)) @@ -118,7 +118,7 @@ trait StagedWasmEvaluator extends SAIOps { val (_, newCtx) = Stack.pop() eval(rest, kont, mkont, trail)(newCtx) case WasmConst(num) => - val newCtx = Stack.push(num) + val newCtx = Stack.push(toStagedNum(num)) eval(rest, kont, mkont, trail)(newCtx) case LocalGet(i) => val newCtx = Stack.push(Frames.get(i)) @@ -155,7 +155,10 @@ trait StagedWasmEvaluator extends SAIOps { case MemorySize => ??? case MemoryGrow => val (delta, newCtx1) = Stack.pop() - val newCtx2 = Stack.push(Values.I32V(Memory.grow(delta.toInt)))(newCtx1) + val ret = Memory.grow(delta.toInt) + val retNum = Values.I32V(ret) + val retSym = "Concrete".reflectCtrlWith[SymVal](retNum) + val newCtx2 = Stack.push(I32(retNum, retSym))(newCtx1) eval(rest, kont, mkont, trail)(newCtx2) case MemoryFill => ??? case Unreachable => unreachable() @@ -220,6 +223,7 @@ trait StagedWasmEvaluator extends SAIOps { val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) eval(rest, kont, mk, trail)(newRestCtx) }) + // TODO: put the cond.s to path condition if (cond.toInt != 0) { eval(thn, restK _, mkont, restK _ :: trail)(newCtx) } else { @@ -232,6 +236,7 @@ trait StagedWasmEvaluator extends SAIOps { case BrIf(label) => val (cond, newCtx) = Stack.pop() info(s"The br_if(${label})'s condition is ", cond.toInt) + // TODO: put the cond.s to path condition if (cond.toInt != 0) { info(s"Jump to $label") trail(label)(newCtx)(mkont) @@ -320,7 +325,7 @@ trait StagedWasmEvaluator extends SAIOps { } def evalTestOp(op: TestOp, value: StagedNum): StagedNum = op match { - case Eqz(_) => Values.I32V(if (value.toInt == 0) 1 else 0) + case Eqz(_) => value.isZero } def evalUnaryOp(op: UnaryOp, value: StagedNum): StagedNum = op match { @@ -523,6 +528,7 @@ trait StagedWasmEvaluator extends SAIOps { I32("I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset)), "sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) } + // Returns the previous memory size on success, or -1 if the memory cannot be grown. def grow(delta: Rep[Int]): Rep[Int] = { "memory-grow".reflectCtrlWith[Int](delta) } @@ -539,12 +545,12 @@ trait StagedWasmEvaluator extends SAIOps { // runtime values object Values { - def I32V(i: Rep[Int]): StagedNum = { - I32("I32V".reflectCtrlWith[Num](i), "Concrete".reflectCtrlWith[SymVal]("I32V".reflectCtrlWith[Num](i))) + def I32V(i: Rep[Int]): Rep[Num] = { + "I32V".reflectCtrlWith[Num](i) } - def I64V(i: Rep[Long]): StagedNum = { - I64("I64V".reflectCtrlWith[Num](i), "Concrete".reflectCtrlWith[SymVal]("I64V".reflectCtrlWith[Num](i))) + def I64V(i: Rep[Long]): Rep[Num] = { + "I64V".reflectCtrlWith[Num](i) } } @@ -574,6 +580,10 @@ trait StagedWasmEvaluator extends SAIOps { def toInt: Rep[Int] = "num-to-int".reflectCtrlWith[Int](num.i) + def isZero(): StagedNum = num match { + case I32(x_c, x_s) => I32(Values.I32V("is-zero".reflectCtrlWith[Int](num.toInt)), "sym-is-zero".reflectCtrlWith[SymVal](x_s)) + } + def clz(): StagedNum = num match { case I32(x_c, x_s) => I32("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) case I64(x_c, x_s) => I64("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) @@ -750,13 +760,16 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { else if (m.toString.endsWith("Global")) "Global" else if (m.toString.endsWith("I32V")) "I32V" else if (m.toString.endsWith("I64V")) "I64V" + else if (m.toString.endsWith("SymVal")) "SymVal" + else super.remap(m) } - // for now, the traverse/shallow is same as the scala backend's override def traverse(n: Node): Unit = n match { case Node(_, "stack-push", List(value), _) => emit("Stack.push("); shallow(value); emit(");\n") + case Node(_, "sym-stack-push", List(s_value), _) => + emit("SymStack.push("); shallow(s_value); emit(");\n") case Node(_, "stack-drop", List(n), _) => emit("Stack.drop("); shallow(n); emit(");\n") case Node(_, "stack-init", _, _) => @@ -765,12 +778,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.print();\n") case Node(_, "frame-push", List(i), _) => emit("Frames.pushFrame("); shallow(i); emit(");\n") + case Node(_, "sym-frame-push", List(i), _) => + emit("SymFrames.pushFrame("); shallow(i); emit(");\n") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(");\n") - case Node(_, "frame-putAll", List(args), _) => - emit("Frames.putAll("); shallow(args); emit(");\n") case Node(_, "frame-set", List(i, value), _) => emit("Frames.set("); shallow(i); emit(", "); shallow(value); emit(");\n") + case Node(_, "sym-frame-set", List(i, s_value), _) => + emit("SymFrames.set("); shallow(i); emit(", "); shallow(s_value); emit(");\n") case Node(_, "global-set", List(i, value), _) => emit("Global.globalSet("); shallow(i); emit(", "); shallow(value); emit(");\n") // Note: The following code is copied from the traverse of CppBackend.scala, try to avoid duplicated code @@ -787,10 +802,11 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case _ => super.traverse(n) } - // code generation for pure nodes override def shallow(n: Node): Unit = n match { case Node(_, "frame-get", List(i), _) => emit("Frames.get("); shallow(i); emit(")") + case Node(_, "sym-frame-get", List(i), _) => + emit("SymFrames.get("); shallow(i); emit(")") case Node(_, "stack-drop", List(n), _) => emit("Stack.drop("); shallow(n); emit(")") case Node(_, "stack-push", List(value), _) => @@ -799,10 +815,16 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.shift("); shallow(offset); emit(", "); shallow(size); emit(")") case Node(_, "stack-pop", _, _) => emit("Stack.pop()") + case Node(_, "sym-stack-pop", _, _) => + emit("SymStack.pop()") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(")") + case Node(_, "sym-frame-pop", List(i), _) => + emit("SymFrames.popFrame("); shallow(i); emit(")") case Node(_, "stack-peek", _, _) => emit("Stack.peek()") + case Node(_, "sym-stack-peek", _, _) => + emit("SymStack.peek()") case Node(_, "stack-take", List(n), _) => emit("Stack.take("); shallow(n); emit(")") case Node(_, "slice-reverse", List(slice), _) => @@ -817,8 +839,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.size()") case Node(_, "global-get", List(i), _) => emit("Global.globalGet("); shallow(i); emit(")") + case Node(_, "is-zero", List(num), _) => + emit("(0 == "); shallow(num); emit(")") + case Node(_, "sym-is-zero", List(s_num), _) => + shallow(s_num); emit(".is_zero()") case Node(_, "binary-add", List(lhs, rhs), _) => shallow(lhs); emit(" + "); shallow(rhs) + case Node(_, "sym-binary-add", List(lhs, rhs), _) => + shallow(lhs); emit(" + "); shallow(rhs) case Node(_, "binary-sub", List(lhs, rhs), _) => shallow(lhs); emit(" - "); shallow(rhs) case Node(_, "binary-mul", List(lhs, rhs), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala new file mode 100644 index 000000000..eef6ab017 --- /dev/null +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -0,0 +1,33 @@ +package gensym.wasm + +import org.scalatest.FunSuite + +import lms.core.stub.Adapter + +import gensym.wasm.miniwasm.{ModuleInstance} +import gensym.wasm.parser._ +import gensym.wasm.stagedconcolicminiwasm._ + +class TestStagedConcolicEval extends FunSuite { + def testFileToCpp(filename: String, main: Option[String] = None, expect: Option[List[Float]]=None) = { + val moduleInst = ModuleInstance(Parser.parseFile(filename)) + val cppFile = s"$filename.cpp" + val exe = s"$cppFile.exe" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true) + + import sys.process._ + val result = s"./$exe".!! + println(result) + + expect.map(vs => { + val stackValues = result + .split("Stack contents: \n")(1) + .split("\n") + .map(_.toFloat) + .toList + assert(vs == stackValues) + }) + } + + test("ack-cpp") { testFileToCpp("./benchmarks/wasm/ack.wat", Some("real_main"), expect=Some(List(7))) } +} From 8d81fbe2e61a1f7e792be3fb5463d7ead9954ea4 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 9 Jul 2025 19:24:24 +0800 Subject: [PATCH 005/105] record path conditions --- headers/wasm/symbolic_rt.hpp | 18 ++++++++++++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 21 +++++++++++++++++++ 2 files changed, 39 insertions(+) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index d03509acb..05fc41d49 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -17,6 +17,12 @@ class SymVal { // Not implemented yet return SymVal(); } + + SymVal negate() const { + // negate the symbolic condition by creating a new symbolic value + // not implemented yet + return SymVal(); + } }; class SymStack_t { @@ -69,4 +75,16 @@ static SymVal Concrete(Num num) { return SymVal(); } +class ExploreTree_t { +public: + std::monostate fillIfElseNode(SymVal s, bool branch) { + // fill the current node with the branch condition s + // parameter branch is redundant, to hint which branch we've entered + // Not implemented yet + return std::monostate(); + } +}; + +static ExploreTree_t ExploreTree; + #endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index c41c7c42f..1eb717e3d 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -225,8 +225,10 @@ trait StagedWasmEvaluator extends SAIOps { }) // TODO: put the cond.s to path condition if (cond.toInt != 0) { + ExploreTree.fillWithIfElse(cond.s, true) eval(thn, restK _, mkont, restK _ :: trail)(newCtx) } else { + ExploreTree.fillWithIfElse(cond.s.not, false) eval(els, restK _, mkont, restK _ :: trail)(newCtx) } () @@ -239,9 +241,11 @@ trait StagedWasmEvaluator extends SAIOps { // TODO: put the cond.s to path condition if (cond.toInt != 0) { info(s"Jump to $label") + ExploreTree.fillWithIfElse(cond.s, true) trail(label)(newCtx)(mkont) } else { info(s"Continue") + ExploreTree.fillWithIfElse(cond.s.not, false) eval(rest, kont, mkont, trail)(newCtx) } () @@ -575,6 +579,13 @@ trait StagedWasmEvaluator extends SAIOps { } } + // Exploration tree, + object ExploreTree { + def fillWithIfElse(s: Rep[SymVal], branch: Boolean): Rep[Unit] = { + "tree-fill-if-else".reflectCtrlWith[Unit](s, branch) + } + } + // runtime Num type implicit class StagedNumOps(num: StagedNum) { @@ -733,6 +744,12 @@ trait StagedWasmEvaluator extends SAIOps { } } } + + implicit class SymbolicOps(s: Rep[SymVal]) { + def not(): Rep[SymVal] = { + "sym-not".reflectCtrlWith(s) + } + } } trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { @@ -881,6 +898,10 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(" >= "); shallow(rhs) case Node(_, "num-to-int", List(num), _) => shallow(num); emit(".toInt()") + case Node(_, "tree-fill-if-else", List(s, b), _) => + emit("ExploreTree.fillIfElseNode("); shallow(s); emit(", "); shallow(b); emit(")") + case Node(_, "sym-not", List(s), _) => + shallow(s); emit(".negate()") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => From 61215b6c87a2ba1ffa3f88838c17dc3d7e3cfb86 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 9 Jul 2025 23:06:44 +0800 Subject: [PATCH 006/105] The branch node only needs to remember the positive condition. use the sub-nodes of the branch to classify whether the execution is true or false --- headers/wasm/symbolic_rt.hpp | 6 ++++- .../scala/wasm/StagedConcolicMiniWasm.scala | 24 ++++++++++++------- 2 files changed, 21 insertions(+), 9 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 05fc41d49..a0199db48 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -77,12 +77,16 @@ static SymVal Concrete(Num num) { class ExploreTree_t { public: - std::monostate fillIfElseNode(SymVal s, bool branch) { + std::monostate fillIfElseNode(SymVal s) { // fill the current node with the branch condition s // parameter branch is redundant, to hint which branch we've entered // Not implemented yet return std::monostate(); } + + std::monostate moveCursor(bool branch) { + return std::monostate(); + } }; static ExploreTree_t ExploreTree; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 1eb717e3d..d31af3cb7 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -224,11 +224,12 @@ trait StagedWasmEvaluator extends SAIOps { eval(rest, kont, mk, trail)(newRestCtx) }) // TODO: put the cond.s to path condition + ExploreTree.fillWithIfElse(cond.s) if (cond.toInt != 0) { - ExploreTree.fillWithIfElse(cond.s, true) + ExploreTree.moveCursor(true) eval(thn, restK _, mkont, restK _ :: trail)(newCtx) } else { - ExploreTree.fillWithIfElse(cond.s.not, false) + ExploreTree.moveCursor(false) eval(els, restK _, mkont, restK _ :: trail)(newCtx) } () @@ -239,13 +240,14 @@ trait StagedWasmEvaluator extends SAIOps { val (cond, newCtx) = Stack.pop() info(s"The br_if(${label})'s condition is ", cond.toInt) // TODO: put the cond.s to path condition + ExploreTree.fillWithIfElse(cond.s) if (cond.toInt != 0) { info(s"Jump to $label") - ExploreTree.fillWithIfElse(cond.s, true) + ExploreTree.moveCursor(true) trail(label)(newCtx)(mkont) } else { info(s"Continue") - ExploreTree.fillWithIfElse(cond.s.not, false) + ExploreTree.moveCursor(false) eval(rest, kont, mkont, trail)(newCtx) } () @@ -581,8 +583,12 @@ trait StagedWasmEvaluator extends SAIOps { // Exploration tree, object ExploreTree { - def fillWithIfElse(s: Rep[SymVal], branch: Boolean): Rep[Unit] = { - "tree-fill-if-else".reflectCtrlWith[Unit](s, branch) + def fillWithIfElse(s: Rep[SymVal]): Rep[Unit] = { + "tree-fill-if-else".reflectCtrlWith[Unit](s) + } + + def moveCursor(branch: Boolean): Rep[Unit] = { + "tree-move-cursor".reflectCtrlWith[Unit](branch) } } @@ -898,8 +904,10 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(" >= "); shallow(rhs) case Node(_, "num-to-int", List(num), _) => shallow(num); emit(".toInt()") - case Node(_, "tree-fill-if-else", List(s, b), _) => - emit("ExploreTree.fillIfElseNode("); shallow(s); emit(", "); shallow(b); emit(")") + case Node(_, "tree-fill-if-else", List(s), _) => + emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") + case Node(_, "tree-move-cursor", List(b), _) => + emit("ExploreTree.moveCursor("); shallow(b); emit(")") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") case Node(_, "dummy", _, _) => emit("std::monostate()") From d18b5f7ca62dc6a96baca04eb38f638d06e41b0b Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 13 Jul 2025 14:57:36 +0800 Subject: [PATCH 007/105] symbolic runtime for explore tree --- headers/wasm/symbolic_rt.hpp | 86 ++++++++++++++++++- .../scala/wasm/StagedConcolicMiniWasm.scala | 8 ++ 2 files changed, 90 insertions(+), 4 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index a0199db48..4373af849 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -2,6 +2,9 @@ #define WASM_SYMBOLIC_RT_HPP #include "concrete_rt.hpp" +#include +#include +#include #include class SymVal { @@ -75,18 +78,93 @@ static SymVal Concrete(Num num) { return SymVal(); } +struct Node; + +struct NodeBox { + explicit NodeBox(); + std::unique_ptr node; + NodeBox *parent; +}; + +struct Node { + virtual ~Node(){}; + virtual std::string to_string() = 0; +}; + +struct IfElseNode : Node { + SymVal cond; + std::unique_ptr true_branch; + std::unique_ptr false_branch; + + IfElseNode(SymVal cond) + : cond(cond), true_branch(std::make_unique()), + false_branch(std::make_unique()) {} + + std::string to_string() override { + std::string result = "IfElseNode {\n"; + result += " true_branch: "; + if (true_branch) { + result += true_branch->node->to_string(); + } else { + result += "nullptr"; + } + result += "\n"; + + result += " false_branch: "; + if (false_branch) { + result += false_branch->node->to_string(); + } else { + result += "nullptr"; + } + result += "\n"; + result += "}"; + return result; + } +}; + +struct UnExploredNode : Node { + UnExploredNode() {} + std::string to_string() override { return "UnexploredNode"; } +}; + +static UnExploredNode unexplored; + +inline NodeBox::NodeBox() + : node(std::make_unique< + UnExploredNode>() /* TODO: avoid allocation of unexplored node */) {} + class ExploreTree_t { public: - std::monostate fillIfElseNode(SymVal s) { - // fill the current node with the branch condition s - // parameter branch is redundant, to hint which branch we've entered - // Not implemented yet + explicit ExploreTree_t() + : root(std::make_unique()), cursor(root.get()) {} + std::monostate fillIfElseNode(SymVal cond) { + // fill the current node with an ifelse branch node + cursor->node = std::make_unique(cond); return std::monostate(); } std::monostate moveCursor(bool branch) { + assert(cursor != nullptr); + auto if_else_node = dynamic_cast(cursor->node.get()); + assert( + if_else_node != nullptr && + "Can't move cursor when the branch node is not initialized correctly!"); + if (branch) { + cursor = if_else_node->true_branch.get(); + } else { + cursor = if_else_node->false_branch.get(); + } return std::monostate(); } + + std::monostate print() { + std::cout << root->node->to_string() << std::endl; + return std::monostate(); + } + +private: + std::unique_ptr root; + NodeBox *cursor; }; static ExploreTree_t ExploreTree; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index d31af3cb7..4366ac785 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -16,6 +16,7 @@ import gensym.wasm.miniwasm.{ModuleInstance} import gensym.wasm.symbolic.{SymVal} import gensym.lmsx.{SAIDriver, StringOps, SAIOps, SAICodeGenBase, CppSAIDriver, CppSAICodeGenBase} import gensym.wasm.symbolic.Concrete +import gensym.wasm.symbolic.ExploreTree @virtualize trait StagedWasmEvaluator extends SAIOps { @@ -405,6 +406,7 @@ trait StagedWasmEvaluator extends SAIOps { info("Exiting the program...") if (printRes) { Stack.print() + ExploreTree.print() } "no-op".reflectCtrlWith[Unit]() } @@ -590,6 +592,10 @@ trait StagedWasmEvaluator extends SAIOps { def moveCursor(branch: Boolean): Rep[Unit] = { "tree-move-cursor".reflectCtrlWith[Unit](branch) } + + def print(): Rep[Unit] = { + "tree-print".reflectCtrlWith[Unit]() + } } // runtime Num type @@ -908,6 +914,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") case Node(_, "tree-move-cursor", List(b), _) => emit("ExploreTree.moveCursor("); shallow(b); emit(")") + case Node(_, "tree-print", List(), _) => + emit("ExploreTree.print()") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") case Node(_, "dummy", _, _) => emit("std::monostate()") From 92ab8ba0d03ec8ef8f3dd9a3b43a32d0c1bfc158 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 14 Jul 2025 01:30:20 +0800 Subject: [PATCH 008/105] add a to graphviz method, enhancing debug experience --- headers/wasm/symbolic_rt.hpp | 73 ++++++++++++++++++++++++++++++++++++ 1 file changed, 73 insertions(+) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 4373af849..02c3021cd 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -3,8 +3,10 @@ #include "concrete_rt.hpp" #include +#include #include #include +#include #include class SymVal { @@ -89,8 +91,29 @@ struct NodeBox { struct Node { virtual ~Node(){}; virtual std::string to_string() = 0; + void to_graphviz(std::ostream &os) { + os << "digraph G {\n"; + os << " rankdir=TB;\n"; + os << " node [shape=box, style=filled, fillcolor=lightblue];\n"; + current_id = 0; + generate_dot(os, -1, ""); + + os << "}\n"; + } + int get_next_id(int &id_counter) { return id_counter++; } + virtual int generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) = 0; + +protected: + // Counter for unique node IDs across the entire graph, only for generating + // graphviz purpose + static int current_id; }; +// TODO: use this header file in multiple compilation units will cause problems +// during linking +int Node::current_id = 0; + struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; @@ -120,11 +143,56 @@ struct IfElseNode : Node { result += "}"; return result; } + + int generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id; + current_id += 1; + + os << " node" << current_node_dot_id << " [label=\"If\"," + << "shape=diamond, fillcolor=lightyellow];\n"; + + // Draw edge from parent if this is not the root node + if (parent_dot_id != -1) { + os << " node" << parent_dot_id << " -> node" << current_node_dot_id; + if (!edge_label.empty()) { + os << " [label=\"" << edge_label << "\"]"; + } + os << ";\n"; + } + assert(true_branch != nullptr); + assert(true_branch->node != nullptr); + true_branch->node->generate_dot(os, current_node_dot_id, "true"); + assert(false_branch != nullptr); + assert(false_branch->node != nullptr); + false_branch->node->generate_dot(os, current_node_dot_id, "false"); + return current_node_dot_id; + } }; struct UnExploredNode : Node { UnExploredNode() {} std::string to_string() override { return "UnexploredNode"; } + +protected: + int generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + + os << " node" << current_node_dot_id + << " [label=\"Unexplored\", shape=octagon, style=filled, " + "fillcolor=lightgrey];\n"; + + if (parent_dot_id != -1) { + os << " node" << parent_dot_id << " -> node" << current_node_dot_id; + if (!edge_label.empty()) { + os << " [label=\"" << edge_label << "\"]"; + } + os << ";\n"; + } + + return current_node_dot_id; + } }; static UnExploredNode unexplored; @@ -162,6 +230,11 @@ class ExploreTree_t { return std::monostate(); } + std::monostate to_graphviz(std::ostream &os) { + root->node->to_graphviz(os); + return std::monostate(); + } + private: std::unique_ptr root; NodeBox *cursor; From e1d7fc8fe801a877c8ef7e09d904e8714f6bbd17 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 14 Jul 2025 23:49:20 +0800 Subject: [PATCH 009/105] put symbolic expression on the SymStack --- headers/wasm/symbolic_rt.hpp | 126 +++++++++++++++++++++++++---------- 1 file changed, 92 insertions(+), 34 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 02c3021cd..fac3ce6d5 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -8,42 +8,104 @@ #include #include #include +#include -class SymVal { +class Symbolic {}; + +class SymConcrete : public Symbolic { public: - SymVal operator+(const SymVal &other) const { - // Define how to add two symbolic values - // Not implemented yet - return SymVal(); - } + Num value; + SymConcrete(Num num) : value(num) {} +}; - SymVal is_zero() const { - // Check if the symbolic value is zero - // Not implemented yet - return SymVal(); - } +struct SymBinary; - SymVal negate() const { - // negate the symbolic condition by creating a new symbolic value - // not implemented yet - return SymVal(); - } +struct SymVal { + std::shared_ptr symptr; + + SymVal() : symptr(nullptr) {} + SymVal(std::shared_ptr symptr) : symptr(symptr) {} + + SymVal add(const SymVal &other) const; + SymVal minus(const SymVal &other) const; + SymVal mul(const SymVal &other) const; + SymVal div(const SymVal &other) const; + SymVal eq(const SymVal &other) const; + SymVal neq(const SymVal &other) const; + SymVal lt(const SymVal &other) const; + SymVal leq(const SymVal &other) const; + SymVal gt(const SymVal &other) const; + SymVal geq(const SymVal &other) const; +}; + +inline SymVal Concrete(Num num) { + return SymVal(std::make_shared(num)); +} + +enum Operation { ADD, SUB, MUL, DIV, EQ, NEQ, LT, LEQ, GT, GEQ }; + +struct SymBinary : Symbolic { + Operation op; + SymVal lhs; + SymVal rhs; + + SymBinary(Operation op, SymVal lhs, SymVal rhs) + : op(op), lhs(lhs), rhs(rhs) {} }; +inline SymVal SymVal::add(const SymVal &other) const { + return SymVal(std::make_shared(ADD, this, other)); +} + +inline SymVal SymVal::minus(const SymVal &other) const { + return SymVal(std::make_shared(SUB, this, other)); +} + +inline SymVal SymVal::mul(const SymVal &other) const { + return SymVal(std::make_shared(MUL, this, other)); +} + +inline SymVal SymVal::div(const SymVal &other) const { + return SymVal(std::make_shared(DIV, this, other)); +} + +inline SymVal SymVal::eq(const SymVal &other) const { + return SymVal(std::make_shared(EQ, this, other)); +} + +inline SymVal SymVal::neq(const SymVal &other) const { + return SymVal(std::make_shared(NEQ, this, other)); +} +inline SymVal SymVal::lt(const SymVal &other) const { + return SymVal(std::make_shared(LT, this, other)); +} +inline SymVal SymVal::leq(const SymVal &other) const { + return SymVal(std::make_shared(LEQ, this, other)); +} +inline SymVal SymVal::gt(const SymVal &other) const { + return SymVal(std::make_shared(GT, this, other)); +} +inline SymVal SymVal::geq(const SymVal &other) const { + return SymVal(std::make_shared(GEQ, this, other)); +} + class SymStack_t { public: void push(SymVal val) { // Push a symbolic value to the stack - // Not implemented yet + stack.push_back(val); } SymVal pop() { // Pop a symbolic value from the stack - // Not implemented yet - return SymVal(); + auto ret = stack.back(); + stack.pop_back(); + return ret; } - SymVal peek() { return SymVal(); } + SymVal peek() { return stack.back(); } + + std::vector stack; }; static SymStack_t SymStack; @@ -52,34 +114,30 @@ class SymFrames_t { public: void pushFrame(int size) { // Push a new frame with the given size - // Not implemented yet + stack.resize(size + stack.size()); } std::monostate popFrame(int size) { // Pop the frame of the given size - // Not implemented yet + stack.resize(stack.size() - size); return std::monostate(); } SymVal get(int index) { - // Get the symbolic value at the given index - // Not implemented yet - return SymVal(); + // Get the symbolic value at the given frame index + return stack[stack.size() - 1 - index]; } void set(int index, SymVal val) { // Set the symbolic value at the given index // Not implemented yet + stack[stack.size() - 1 - index] = val; } + + std::vector stack; }; static SymFrames_t SymFrames; -static SymVal Concrete(Num num) { - // Convert a concrete number to a symbolic value - // Not implemented yet - return SymVal(); -} - struct Node; struct NodeBox { @@ -115,11 +173,11 @@ struct Node { int Node::current_id = 0; struct IfElseNode : Node { - SymVal cond; + Symbolic cond; std::unique_ptr true_branch; std::unique_ptr false_branch; - IfElseNode(SymVal cond) + IfElseNode(Symbolic cond) : cond(cond), true_branch(std::make_unique()), false_branch(std::make_unique()) {} @@ -205,7 +263,7 @@ class ExploreTree_t { public: explicit ExploreTree_t() : root(std::make_unique()), cursor(root.get()) {} - std::monostate fillIfElseNode(SymVal cond) { + std::monostate fillIfElseNode(Symbolic cond) { // fill the current node with an ifelse branch node cursor->node = std::make_unique(cond); return std::monostate(); From 77a4e6f58547a71a5544779f06f41e92b5398375 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 16 Jul 2025 22:50:08 +0800 Subject: [PATCH 010/105] `type.symbolic` instruction --- headers/wasm/symbolic_rt.hpp | 70 +++++++++++++++---- .../scala/wasm/StagedConcolicMiniWasm.scala | 62 +++++++++++++++- .../genwasym/TestStagedConcolicEval.scala | 4 ++ 3 files changed, 120 insertions(+), 16 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index fac3ce6d5..e0d3feef2 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -10,7 +10,19 @@ #include #include -class Symbolic {}; +class Symbolic { +public: + Symbolic() {} // TODO: remove this default constructor later + virtual ~Symbolic() = default; // Make Symbolic polymorphic +}; + +class Symbol : public Symbolic { +public: + Symbol(int id) : id(id) {} + +private: + int id; +}; class SymConcrete : public Symbolic { public: @@ -26,6 +38,11 @@ struct SymVal { SymVal() : symptr(nullptr) {} SymVal(std::shared_ptr symptr) : symptr(symptr) {} + // data structure operations + SymVal makeSymbolic() const; + + // arithmetic operations + SymVal is_zero() const; SymVal add(const SymVal &other) const; SymVal minus(const SymVal &other) const; SymVal mul(const SymVal &other) const; @@ -54,39 +71,53 @@ struct SymBinary : Symbolic { }; inline SymVal SymVal::add(const SymVal &other) const { - return SymVal(std::make_shared(ADD, this, other)); + return SymVal(std::make_shared(ADD, *this, other)); } inline SymVal SymVal::minus(const SymVal &other) const { - return SymVal(std::make_shared(SUB, this, other)); + return SymVal(std::make_shared(SUB, *this, other)); } inline SymVal SymVal::mul(const SymVal &other) const { - return SymVal(std::make_shared(MUL, this, other)); + return SymVal(std::make_shared(MUL, *this, other)); } inline SymVal SymVal::div(const SymVal &other) const { - return SymVal(std::make_shared(DIV, this, other)); + return SymVal(std::make_shared(DIV, *this, other)); } inline SymVal SymVal::eq(const SymVal &other) const { - return SymVal(std::make_shared(EQ, this, other)); + return SymVal(std::make_shared(EQ, *this, other)); } inline SymVal SymVal::neq(const SymVal &other) const { - return SymVal(std::make_shared(NEQ, this, other)); + return SymVal(std::make_shared(NEQ, *this, other)); } inline SymVal SymVal::lt(const SymVal &other) const { - return SymVal(std::make_shared(LT, this, other)); + return SymVal(std::make_shared(LT, *this, other)); } inline SymVal SymVal::leq(const SymVal &other) const { - return SymVal(std::make_shared(LEQ, this, other)); + return SymVal(std::make_shared(LEQ, *this, other)); } inline SymVal SymVal::gt(const SymVal &other) const { - return SymVal(std::make_shared(GT, this, other)); + return SymVal(std::make_shared(GT, *this, other)); } inline SymVal SymVal::geq(const SymVal &other) const { - return SymVal(std::make_shared(GEQ, this, other)); + return SymVal(std::make_shared(GEQ, *this, other)); +} +inline SymVal SymVal::is_zero() const { + return SymVal(std::make_shared(EQ, *this, Concrete(I32V(0)))); +} + +inline SymVal SymVal::makeSymbolic() const { + auto concrete = dynamic_cast(symptr.get()); + if (concrete) { + // If the symbolic value is a concrete value, use it to create a symbol + return SymVal(std::make_shared(concrete->value.toInt())); + } else { + throw std::runtime_error( + "Cannot make symbolic a non-concrete symbolic value"); + } } class SymStack_t { @@ -173,11 +204,11 @@ struct Node { int Node::current_id = 0; struct IfElseNode : Node { - Symbolic cond; + SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; - IfElseNode(Symbolic cond) + IfElseNode(SymVal cond) : cond(cond), true_branch(std::make_unique()), false_branch(std::make_unique()) {} @@ -263,7 +294,7 @@ class ExploreTree_t { public: explicit ExploreTree_t() : root(std::make_unique()), cursor(root.get()) {} - std::monostate fillIfElseNode(Symbolic cond) { + std::monostate fillIfElseNode(SymVal cond) { // fill the current node with an ifelse branch node cursor->node = std::make_unique(cond); return std::monostate(); @@ -300,4 +331,15 @@ class ExploreTree_t { static ExploreTree_t ExploreTree; +class SymEnv_t { +public: + Num read(SymVal sym) { + // Read a symbolic value from the symbolic environment + // For now, we just return a zero + return Num(0); + } +}; + +static SymEnv_t SymEnv; + #endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 4366ac785..01bb91c20 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -57,6 +57,15 @@ trait StagedWasmEvaluator extends SAIOps { case NumType(F32Type) => 4 case NumType(F64Type) => 8 } + + def toTagger: (Rep[Num], Rep[SymVal]) => StagedNum = { + ty match { + case NumType(I32Type) => I32 + case NumType(I64Type) => I64 + case NumType(F32Type) => F32 + case NumType(F64Type) => F64 + } + } } case class Context( @@ -121,6 +130,14 @@ trait StagedWasmEvaluator extends SAIOps { case WasmConst(num) => val newCtx = Stack.push(toStagedNum(num)) eval(rest, kont, mkont, trail)(newCtx) + case Symbolic(ty) => + val (id, newCtx1) = Stack.pop() + val symVal = id.makeSymbolic() + val concVal = SymEnv.read(symVal) + val tagger = ty.toTagger + val value = tagger(concVal, symVal) + val newCtx2 = Stack.push(value)(newCtx1) + eval(rest, kont, mkont, trail)(newCtx2) case LocalGet(i) => val newCtx = Stack.push(Frames.get(i)) eval(rest, kont, mkont, trail)(newCtx) @@ -326,6 +343,10 @@ trait StagedWasmEvaluator extends SAIOps { val (v, newCtx) = Stack.pop() println(v.toInt) eval(rest, kont, mkont, trail)(newCtx) + case Import("console", "assert", _) => + val (v, newCtx) = Stack.pop() + runtimeAssert(v.toInt != 0) + eval(rest, kont, mkont, trail)(newCtx) case Import(_, _, _) => throw new Exception(s"Unknown import at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } @@ -414,6 +435,10 @@ trait StagedWasmEvaluator extends SAIOps { evalTop(temp, main) } + def runtimeAssert(b: Rep[Boolean]): Rep[Unit] = { + "assert-true".reflectCtrlWith[Unit](b) + } + // stack operations object Stack { def shift(offset: Int, size: Int)(ctx: Context): Context = { @@ -598,6 +623,12 @@ trait StagedWasmEvaluator extends SAIOps { } } + object SymEnv { + def read(sym: Rep[SymVal]): Rep[Num] = { + "sym-env-read".reflectCtrlWith[Num](sym) + } + } + // runtime Num type implicit class StagedNumOps(num: StagedNum) { @@ -622,6 +653,10 @@ trait StagedWasmEvaluator extends SAIOps { case I64(x_c, x_s) => I64("popcnt".reflectCtrlWith[Num](x_c), "sym-popcnt".reflectCtrlWith[SymVal](x_s)) } + def makeSymbolic(): Rep[SymVal] = { + "make-symbolic".reflectCtrlWith[SymVal](num.s) + } + def +(rhs: StagedNum): StagedNum = { (num, rhs) match { case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) @@ -778,6 +813,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { override def mayInline(n: Node): Boolean = n match { case Node(_, "stack-pop", _, _) | Node(_, "stack-peek", _, _) + | Node(_, "sym-stack-pop", _, _) => false case _ => super.mayInline(n) } @@ -874,8 +910,6 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(s_num); emit(".is_zero()") case Node(_, "binary-add", List(lhs, rhs), _) => shallow(lhs); emit(" + "); shallow(rhs) - case Node(_, "sym-binary-add", List(lhs, rhs), _) => - shallow(lhs); emit(" + "); shallow(rhs) case Node(_, "binary-sub", List(lhs, rhs), _) => shallow(lhs); emit(" - "); shallow(rhs) case Node(_, "binary-mul", List(lhs, rhs), _) => @@ -908,8 +942,32 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(" >= "); shallow(rhs) case Node(_, "relation-geu", List(lhs, rhs), _) => shallow(lhs); emit(" >= "); shallow(rhs) + case Node(_, "sym-binary-add", List(lhs, rhs), _) => + shallow(lhs); emit(".add("); shallow(rhs); emit(")") + case Node(_, "sym-binary-mul", List(lhs, rhs), _) => + shallow(lhs); emit(".mul("); shallow(rhs); emit(")") + case Node(_, "sym-binary-div", List(lhs, rhs), _) => + shallow(lhs); emit(".div("); shallow(rhs); emit(")") + case Node(_, "sym-relation-le", List(lhs, rhs), _) => + shallow(lhs); emit(".leq("); shallow(rhs); emit(")") + case Node(_, "sym-relation-leu", List(lhs, rhs), _) => + shallow(lhs); emit(".leu("); shallow(rhs); emit(")") + case Node(_, "sym-relation-ge", List(lhs, rhs), _) => + shallow(lhs); emit(".ge("); shallow(rhs); emit(")") + case Node(_, "sym-relation-geu", List(lhs, rhs), _) => + shallow(lhs); emit(".geu("); shallow(rhs); emit(")") + case Node(_, "sym-relation-eq", List(lhs, rhs), _) => + shallow(lhs); emit(".eq("); shallow(rhs); emit(")") + case Node(_, "sym-relation-ne", List(lhs, rhs), _) => + shallow(lhs); emit(".neq("); shallow(rhs); emit(")") case Node(_, "num-to-int", List(num), _) => shallow(num); emit(".toInt()") + case Node(_, "make-symbolic", List(num), _) => + shallow(num); emit(".makeSymbolic()") + case Node(_, "sym-env-read", List(sym), _) => + emit("SymEnv.read("); shallow(sym); emit(")") + case Node(_, "assert-true", List(cond), _) => + emit("assert("); shallow(cond); emit(")") case Node(_, "tree-fill-if-else", List(s), _) => emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") case Node(_, "tree-move-cursor", List(b), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index eef6ab017..409bd07a2 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -30,4 +30,8 @@ class TestStagedConcolicEval extends FunSuite { } test("ack-cpp") { testFileToCpp("./benchmarks/wasm/ack.wat", Some("real_main"), expect=Some(List(7))) } + + test("bug-finding") { + testFileToCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) + } } From 314ff5fe8b848cb1f40ee774283489c0760eec35 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 16 Jul 2025 23:11:33 +0800 Subject: [PATCH 011/105] test staged concolic compilation in CI --- .github/workflows/scala.yml | 1 + benchmarks/wasm/branch-strip-buggy.wat | 1 + 2 files changed, 2 insertions(+) diff --git a/.github/workflows/scala.yml b/.github/workflows/scala.yml index 4677da77f..d2f8348ba 100644 --- a/.github/workflows/scala.yml +++ b/.github/workflows/scala.yml @@ -79,3 +79,4 @@ jobs: sbt 'testOnly gensym.wasm.TestConcolic' sbt 'testOnly gensym.wasm.TestDriver' sbt 'testOnly gensym.wasm.TestStagedEval' + sbt 'testOnly gensym.wasm.TestStagedConcolicEval' diff --git a/benchmarks/wasm/branch-strip-buggy.wat b/benchmarks/wasm/branch-strip-buggy.wat index c957db7f6..0685f0be1 100644 --- a/benchmarks/wasm/branch-strip-buggy.wat +++ b/benchmarks/wasm/branch-strip-buggy.wat @@ -29,6 +29,7 @@ else i32.const 0 call 2 + i32.const 1 ;; to satisfy the type checker, this line will never be reached end end ) From 873936902fe34538c698fbd664df370b9133003c Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 17 Jul 2025 00:18:51 +0800 Subject: [PATCH 012/105] dump graphviz by default --- headers/wasm/symbolic_rt.hpp | 10 +++++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 22 ++++++++++++++----- .../genwasym/TestStagedConcolicEval.scala | 3 ++- 3 files changed, 28 insertions(+), 7 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index e0d3feef2..a97fd0dd5 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -4,6 +4,7 @@ #include "concrete_rt.hpp" #include #include +#include #include #include #include @@ -324,6 +325,15 @@ class ExploreTree_t { return std::monostate(); } + std::monostate dump_graphviz(std::string filepath) { + std::ofstream ofs(filepath); + if (!ofs.is_open()) { + throw std::runtime_error("Failed to open explore_tree.dot for writing"); + } + to_graphviz(ofs); + return std::monostate(); + } + private: std::unique_ptr root; NodeBox *cursor; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 01bb91c20..3c342177d 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -422,12 +422,15 @@ trait StagedWasmEvaluator extends SAIOps { Frames.popFrame(locals.size) } - def evalTop(main: Option[String], printRes: Boolean = false): Rep[Unit] = { + def evalTop(main: Option[String], printRes: Boolean, dumpTree: Option[String]): Rep[Unit] = { val haltK: Rep[Unit] => Rep[Unit] = (_) => { info("Exiting the program...") if (printRes) { Stack.print() - ExploreTree.print() + } + dumpTree match { + case Some(filePath) => ExploreTree.dumpGraphiviz(filePath) + case None => () } "no-op".reflectCtrlWith[Unit]() } @@ -621,6 +624,10 @@ trait StagedWasmEvaluator extends SAIOps { def print(): Rep[Unit] = { "tree-print".reflectCtrlWith[Unit]() } + + def dumpGraphiviz(filePath: String): Rep[Unit] = { + "tree-dump-graphviz".reflectCtrlWith[Unit](filePath) + } } object SymEnv { @@ -974,6 +981,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.moveCursor("); shallow(b); emit(")") case Node(_, "tree-print", List(), _) => emit("ExploreTree.print()") + case Node(_, "tree-dump-graphviz", List(f), _) => + emit("ExploreTree.dump_graphviz("); shallow(f); emit(")") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") case Node(_, "dummy", _, _) => emit("std::monostate()") @@ -1033,12 +1042,12 @@ trait WasmToCppCompilerDriver[A, B] extends CppSAIDriver[A, B] with StagedWasmEv object WasmToCppCompiler { case class GeneratedCpp(source: String, headerFolders: List[String]) - def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean = false): GeneratedCpp = { + def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean, dumpTree: Option[String]): GeneratedCpp = { println(s"Now compiling wasm module with entry function $main") val driver = new WasmToCppCompilerDriver[Unit, Unit] { def module: ModuleInstance = moduleInst def snippet(x: Rep[Unit]): Rep[Unit] = { - evalTop(main, printRes) + evalTop(main, printRes, dumpTree) } } GeneratedCpp(driver.code, driver.codegen.includePaths.toList) @@ -1048,8 +1057,9 @@ object WasmToCppCompiler { main: Option[String], outputCpp: String, outputExe: String, - printRes: Boolean = false): Unit = { - val generated = compile(moduleInst, main, printRes) + printRes: Boolean, + dumpTree: Option[String]): Unit = { + val generated = compile(moduleInst, main, printRes, dumpTree) val code = generated.source val writer = new java.io.PrintWriter(new java.io.File(outputCpp)) diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 409bd07a2..77868e2c2 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -13,7 +13,8 @@ class TestStagedConcolicEval extends FunSuite { val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" val exe = s"$cppFile.exe" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true) + val exploreTreeFile = s"$filename.tree.dot" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, Some(exploreTreeFile)) import sys.process._ val result = s"./$exe".!! From 9a9988c560f58961b2fb09892912623c26b9691e Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 17 Jul 2025 18:15:48 +0800 Subject: [PATCH 013/105] concolic driver --- headers/wasm.hpp | 3 +- headers/wasm/concolic_driver.hpp | 98 +++++++++ headers/wasm/concrete_rt.hpp | 9 +- headers/wasm/smt_solver.hpp | 28 +++ headers/wasm/symbolic_rt.hpp | 205 +++++++++++++++--- headers/wasm/utils.hpp | 15 ++ .../scala/wasm/StagedConcolicMiniWasm.scala | 20 +- 7 files changed, 338 insertions(+), 40 deletions(-) create mode 100644 headers/wasm/concolic_driver.hpp create mode 100644 headers/wasm/smt_solver.hpp create mode 100644 headers/wasm/utils.hpp diff --git a/headers/wasm.hpp b/headers/wasm.hpp index c7e98b6eb..36fe3849f 100644 --- a/headers/wasm.hpp +++ b/headers/wasm.hpp @@ -3,5 +3,6 @@ #include "wasm/concrete_rt.hpp" #include "wasm/symbolic_rt.hpp" - +#include "wasm/concolic_driver.hpp" +#include "wasm/utils.hpp" #endif \ No newline at end of file diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp new file mode 100644 index 000000000..4307413bd --- /dev/null +++ b/headers/wasm/concolic_driver.hpp @@ -0,0 +1,98 @@ +#ifndef CONCOLIC_DRIVER_HPP +#define CONCOLIC_DRIVER_HPP + +#include "smt_solver.hpp" +#include "symbolic_rt.hpp" +#include +#include +#include + +class ConcolicDriver { + friend class ManagedConcolicCleanup; + +public: + ConcolicDriver(std::function entrypoint, std::string tree_file) + : entrypoint(entrypoint), tree_file(tree_file) {} + ConcolicDriver(std::function entrypoint) + : entrypoint(entrypoint), tree_file(std::nullopt) {} + void run(); + +private: + Solver solver; + std::function entrypoint; + std::optional tree_file; +}; + +class ManagedConcolicCleanup { + const ConcolicDriver &driver; + +public: + ManagedConcolicCleanup(const ConcolicDriver &driver) : driver(driver) {} + ~ManagedConcolicCleanup() { + if (driver.tree_file.has_value()) + ExploreTree.dump_graphviz(driver.tree_file.value()); + } +}; + +inline void ConcolicDriver::run() { + ManagedConcolicCleanup cleanup{*this}; + while (true) { + auto cond = ExploreTree.get_unexplored_conditions(); + ExploreTree.reset_cursor(); + + if (!cond.has_value()) { + std::cout << "No unexplored conditions found, exiting..." << std::endl; + return; + } + auto new_env = solver.solve(cond.value()); + if (!new_env.has_value()) { + std::cout << "All unexplored paths are unreachable, exiting..." + << std::endl; + return; + } + SymEnv.update(std::move(new_env.value())); + try { + entrypoint(); + std::cout << "Execution finished successfully with symbolic environment:" + << std::endl; + std::cout << SymEnv.to_string() << std::endl; + } catch (...) { + ExploreTree.fillFailedNode(); + std::cout << "Caught runtime error with symbolic environment:" + << std::endl; + std::cout << SymEnv.to_string() << std::endl; + return; + } + } +} + +static std::monostate reset_stacks() { + Stack.reset(); + Frames.reset(); + SymStack.reset(); + SymFrames.reset(); + initRand(); + Memory = Memory_t(1); + return std::monostate{}; +} + +static void start_concolic_execution_with( + std::function entrypoint, + std::string tree_file) { + ConcolicDriver driver([=]() { entrypoint(std::monostate{}); }, tree_file); + driver.run(); +} + +static void start_concolic_execution_with( + std::function entrypoint) { + + const char *env_tree_file = std::getenv("TREE_FILE"); + + ConcolicDriver driver = + env_tree_file ? ConcolicDriver([=]() { entrypoint(std::monostate{}); }, + env_tree_file) + : ConcolicDriver([=]() { entrypoint(std::monostate{}); }); + driver.run(); +} + +#endif // CONCOLIC_DRIVER_HPP \ No newline at end of file diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index e994cbde7..a09614537 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -52,8 +52,6 @@ static Num I32V(int v) { return v; } static Num I64V(int64_t v) { return v; } -using Slice = std::vector; - const int STACK_SIZE = 1024 * 64; class Stack_t { @@ -118,9 +116,12 @@ class Stack_t { } void initialize() { - // do nothing for now + // todo: remove this method + reset(); } + void reset() { count = 0; } + private: int32_t count; Num *stack_ptr; @@ -151,6 +152,8 @@ class Frames_t { count += size; } + void reset() { count = 0; } + private: int32_t count; Num *stack_ptr; diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp new file mode 100644 index 000000000..a3bbf78d4 --- /dev/null +++ b/headers/wasm/smt_solver.hpp @@ -0,0 +1,28 @@ +#ifndef SMT_SOLVER_HPP +#define SMT_SOLVER_HPP + +#include "concrete_rt.hpp" +#include "symbolic_rt.hpp" +#include +#include + +class Solver { +public: + Solver() : count(0) { + envs[0] = {Num(0), Num(0)}; + envs[1] = {Num(1), Num(2)}; + } + std::optional> solve(const std::vector &conditions) { + // here is just a placeholder implementation to simulate solving result + if (count >= envs.size()) { + return std::nullopt; // No more environments to return + } + return envs[count++ % envs.size()]; + } + +private: + std::array, 5> envs; + int count; +}; + +#endif // SMT_SOLVER_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index a97fd0dd5..920bcad42 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -7,7 +7,9 @@ #include #include #include +#include #include +#include #include #include @@ -20,6 +22,7 @@ class Symbolic { class Symbol : public Symbolic { public: Symbol(int id) : id(id) {} + int get_id() const { return id; } private: int id; @@ -54,6 +57,7 @@ struct SymVal { SymVal leq(const SymVal &other) const; SymVal gt(const SymVal &other) const; SymVal geq(const SymVal &other) const; + SymVal negate() const; }; inline SymVal Concrete(Num num) { @@ -109,6 +113,9 @@ inline SymVal SymVal::geq(const SymVal &other) const { inline SymVal SymVal::is_zero() const { return SymVal(std::make_shared(EQ, *this, Concrete(I32V(0)))); } +inline SymVal SymVal::negate() const { + return SymVal(std::make_shared(EQ, *this, Concrete(I32V(0)))); +} inline SymVal SymVal::makeSymbolic() const { auto concrete = dynamic_cast(symptr.get()); @@ -137,6 +144,11 @@ class SymStack_t { SymVal peek() { return stack.back(); } + void reset() { + // Reset the symbolic stack + stack.clear(); + } + std::vector stack; }; @@ -165,6 +177,11 @@ class SymFrames_t { stack[stack.size() - 1 - index] = val; } + void reset() { + // Reset the symbolic frames + stack.clear(); + } + std::vector stack; }; @@ -190,14 +207,28 @@ struct Node { os << "}\n"; } - int get_next_id(int &id_counter) { return id_counter++; } - virtual int generate_dot(std::ostream &os, int parent_dot_id, - const std::string &edge_label) = 0; + virtual void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) = 0; protected: // Counter for unique node IDs across the entire graph, only for generating // graphviz purpose static int current_id; + void graphviz_node(std::ostream &os, const int node_id, + const std::string &label, const std::string &shape, + const std::string &fillcolor) { + os << " node" << node_id << " [label=\"" << label << "\", shape=" << shape + << ", style=filled, fillcolor=" << fillcolor << "];\n"; + } + + void graphviz_edge(std::ostream &os, int from_id, int target_id, + const std::string &edge_label) { + os << " node" << from_id << " -> node" << target_id; + if (!edge_label.empty()) { + os << " [label=\"" << edge_label << "\"]"; + } + os << ";\n"; + } }; // TODO: use this header file in multiple compilation units will cause problems @@ -234,21 +265,16 @@ struct IfElseNode : Node { return result; } - int generate_dot(std::ostream &os, int parent_dot_id, - const std::string &edge_label) override { + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { int current_node_dot_id = current_id; current_id += 1; - os << " node" << current_node_dot_id << " [label=\"If\"," - << "shape=diamond, fillcolor=lightyellow];\n"; + graphviz_node(os, current_node_dot_id, "If", "diamond", "lightyellow"); // Draw edge from parent if this is not the root node if (parent_dot_id != -1) { - os << " node" << parent_dot_id << " -> node" << current_node_dot_id; - if (!edge_label.empty()) { - os << " [label=\"" << edge_label << "\"]"; - } - os << ";\n"; + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); } assert(true_branch != nullptr); assert(true_branch->node != nullptr); @@ -256,7 +282,6 @@ struct IfElseNode : Node { assert(false_branch != nullptr); assert(false_branch->node != nullptr); false_branch->node->generate_dot(os, current_node_dot_id, "false"); - return current_node_dot_id; } }; @@ -265,39 +290,92 @@ struct UnExploredNode : Node { std::string to_string() override { return "UnexploredNode"; } protected: - int generate_dot(std::ostream &os, int parent_dot_id, - const std::string &edge_label) override { + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "Unexplored", "octagon", + "lightgrey"); + + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } + } +}; + +struct Finished : Node { + Finished() {} + std::string to_string() override { return "FinishedNode"; } - os << " node" << current_node_dot_id - << " [label=\"Unexplored\", shape=octagon, style=filled, " - "fillcolor=lightgrey];\n"; +protected: + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "Finished", "box", "lightgreen"); if (parent_dot_id != -1) { - os << " node" << parent_dot_id << " -> node" << current_node_dot_id; - if (!edge_label.empty()) { - os << " [label=\"" << edge_label << "\"]"; - } - os << ";\n"; + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); } + } +}; + +struct Failed : Node { + Failed() {} + std::string to_string() override { return "FailedNode"; } - return current_node_dot_id; +protected: + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "Failed", "box", "red"); + + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } } }; static UnExploredNode unexplored; inline NodeBox::NodeBox() - : node(std::make_unique< - UnExploredNode>() /* TODO: avoid allocation of unexplored node */) {} + : node(std::make_unique()), + /* TODO: avoid allocation of unexplored node */ + parent(nullptr) {} class ExploreTree_t { public: explicit ExploreTree_t() : root(std::make_unique()), cursor(root.get()) {} + + void reset_cursor() { + // Reset the cursor to the root of the tree + cursor = root.get(); + } + + std::monostate fillFinishedNode() { + if (dynamic_cast(cursor->node.get())) { + cursor->node = std::make_unique(); + } else { + assert(dynamic_cast(cursor->node.get()) != nullptr); + } + return std::monostate{}; + } + + std::monostate fillFailedNode() { + if (dynamic_cast(cursor->node.get())) { + cursor->node = std::make_unique(); + } else { + assert(dynamic_cast(cursor->node.get()) != nullptr); + } + return std::monostate{}; + } + std::monostate fillIfElseNode(SymVal cond) { - // fill the current node with an ifelse branch node - cursor->node = std::make_unique(cond); + // fill the current NodeBox with an ifelse branch node it's unexplored + if (dynamic_cast(cursor->node.get())) { + cursor->node = std::make_unique(cond); + } + assert(dynamic_cast(cursor->node.get()) != nullptr && + "Current node is not an IfElseNode, cannot fill it!"); return std::monostate(); } @@ -328,13 +406,60 @@ class ExploreTree_t { std::monostate dump_graphviz(std::string filepath) { std::ofstream ofs(filepath); if (!ofs.is_open()) { - throw std::runtime_error("Failed to open explore_tree.dot for writing"); + throw std::runtime_error("Failed to open " + filepath + " for writing"); } to_graphviz(ofs); return std::monostate(); } + std::optional> get_unexplored_conditions() { + // Get all unexplored conditions in the tree + std::vector result; + auto box = pick_unexplored(); + if (!box) { + return std::nullopt; + } + while (box->parent) { + auto parent = box->parent; + auto if_else_node = dynamic_cast(parent->node.get()); + if (if_else_node) { + if (if_else_node->true_branch.get() == box) { + // If the current box is the true branch, add the condition + result.push_back(if_else_node->cond); + } else if (if_else_node->false_branch.get() == box) { + // If the current box is the false branch, add the negated condition + result.push_back(if_else_node->cond.negate()); + } else { + throw std::runtime_error("Unexpected node structure in explore tree"); + } + } + // Move to parent + box = box->parent; + } + return result; + } + + NodeBox *pick_unexplored() { + // Pick an unexplored node from the tree + // For now, we just iterate through the tree and return the first unexplored + return pick_unexplored_of(root.get()); + } + private: + NodeBox *pick_unexplored_of(NodeBox *node) { + if (dynamic_cast(node->node.get()) != nullptr) { + return node; + } + auto if_else_node = dynamic_cast(node->node.get()); + if (if_else_node) { + NodeBox *result = pick_unexplored_of(if_else_node->true_branch.get()); + if (result) { + return result; + } + return pick_unexplored_of(if_else_node->false_branch.get()); + } + return nullptr; // No unexplored node found + } std::unique_ptr root; NodeBox *cursor; }; @@ -344,10 +469,28 @@ static ExploreTree_t ExploreTree; class SymEnv_t { public: Num read(SymVal sym) { - // Read a symbolic value from the symbolic environment - // For now, we just return a zero return Num(0); + auto symbol = dynamic_cast(sym.symptr.get()); + assert(symbol); + return map[symbol->get_id()]; } + + void update(std::vector new_env) { map = std::move(new_env); } + + std::string to_string() const { + std::string result; + result += "(\n"; + for (int i = 0; i < map.size(); ++i) { + const Num &num = map[i]; + result += + " (" + std::to_string(i) + "->" + std::to_string(num.value) + ")\n"; + } + result += ")"; + return result; + } + +private: + std::vector map; // The symbolic environment, a vector of Num }; static SymEnv_t SymEnv; diff --git a/headers/wasm/utils.hpp b/headers/wasm/utils.hpp new file mode 100644 index 000000000..8a86ac98d --- /dev/null +++ b/headers/wasm/utils.hpp @@ -0,0 +1,15 @@ +#ifndef UTILS_HPP +#define UTILS_HPP + +#ifndef GENSYM_ASSERT +#define GENSYM_ASSERT(condition) \ + do { \ + if (!(condition)) { \ + throw std::runtime_error(std::string("Assertion failed: ") + " (" + \ + __FILE__ + ":" + std::to_string(__LINE__) + \ + ")"); \ + } \ + } while (0) +#endif + +#endif // UTILS_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 3c342177d..71463bf5e 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -416,7 +416,7 @@ trait StagedWasmEvaluator extends SAIOps { } } val (instrs, locals) = (funBody.body, funBody.locals) - Stack.initialize() + resetStacks() Frames.pushFrame(locals) eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) Frames.popFrame(locals.size) @@ -428,10 +428,7 @@ trait StagedWasmEvaluator extends SAIOps { if (printRes) { Stack.print() } - dumpTree match { - case Some(filePath) => ExploreTree.dumpGraphiviz(filePath) - case None => () - } + ExploreTree.fillWithFinished() "no-op".reflectCtrlWith[Unit]() } val temp: Rep[MCont[Unit]] = topFun(haltK) @@ -558,6 +555,7 @@ trait StagedWasmEvaluator extends SAIOps { object Memory { def storeInt(base: Rep[Int], offset: Int, value: Rep[Int]): Rep[Unit] = { "memory-store-int".reflectCtrlWith[Unit](base, offset, value) + // todo: store symbolic value to memory via extract/concat operation } def loadInt(base: Rep[Int], offset: Int): StagedNum = { @@ -570,6 +568,10 @@ trait StagedWasmEvaluator extends SAIOps { } } + def resetStacks(): Rep[Unit] = { + "reset-stacks".reflectCtrlWith[Unit]() + } + // call unreachable def unreachable(): Rep[Unit] = { "unreachable".reflectCtrlWith[Unit]() @@ -617,6 +619,10 @@ trait StagedWasmEvaluator extends SAIOps { "tree-fill-if-else".reflectCtrlWith[Unit](s) } + def fillWithFinished(): Rep[Unit] = { + "tree-fill-finished".reflectCtrlWith[Unit]() + } + def moveCursor(branch: Boolean): Rep[Unit] = { "tree-move-cursor".reflectCtrlWith[Unit](branch) } @@ -875,6 +881,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { } override def shallow(n: Node): Unit = n match { + case Node(_, "reset-stacks", _, _) => + emit("reset_stacks()") case Node(_, "frame-get", List(i), _) => emit("Frames.get("); shallow(i); emit(")") case Node(_, "sym-frame-get", List(i), _) => @@ -977,6 +985,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("assert("); shallow(cond); emit(")") case Node(_, "tree-fill-if-else", List(s), _) => emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") + case Node(_, "tree-fill-finished", List(), _) => + emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b), _) => emit("ExploreTree.moveCursor("); shallow(b); emit(")") case Node(_, "tree-print", List(), _) => From 9ab162fe0305be5c955154b6be9292befe8e4d70 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Fri, 18 Jul 2025 17:41:15 +0800 Subject: [PATCH 014/105] fix: add an unreachable node & use GENSYM_ASSERT --- headers/wasm/concolic_driver.hpp | 16 ++- headers/wasm/symbolic_rt.hpp | 128 ++++++++++++------ .../scala/wasm/StagedConcolicMiniWasm.scala | 2 +- 3 files changed, 97 insertions(+), 49 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 4307413bd..9c35f1614 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -37,18 +37,22 @@ class ManagedConcolicCleanup { inline void ConcolicDriver::run() { ManagedConcolicCleanup cleanup{*this}; while (true) { - auto cond = ExploreTree.get_unexplored_conditions(); ExploreTree.reset_cursor(); - if (!cond.has_value()) { - std::cout << "No unexplored conditions found, exiting..." << std::endl; + auto unexplored = ExploreTree.pick_unexplored(); + if (!unexplored) { + std::cout << "No unexplored nodes found, exiting..." << std::endl; return; } - auto new_env = solver.solve(cond.value()); + auto cond = unexplored->collect_path_conds(); + auto new_env = solver.solve(cond); if (!new_env.has_value()) { - std::cout << "All unexplored paths are unreachable, exiting..." + // TODO: current implementation is buggy, there could be other reachable + // unexplored paths + std::cout << "Found an unreachable path, marking it as unreachable..." << std::endl; - return; + unexplored->fillUnreachableNode(); + continue; } SymEnv.update(std::move(new_env.value())); try { diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 920bcad42..95f292b55 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -193,6 +193,13 @@ struct NodeBox { explicit NodeBox(); std::unique_ptr node; NodeBox *parent; + + std::monostate fillIfElseNode(SymVal cond); + std::monostate fillFinishedNode(); + std::monostate fillFailedNode(); + std::monostate fillUnreachableNode(); + + std::vector collect_path_conds(); }; struct Node { @@ -334,13 +341,87 @@ struct Failed : Node { } }; -static UnExploredNode unexplored; +struct Unreachable : Node { + Unreachable() {} + std::string to_string() override { return "UnreachableNode"; } + +protected: + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "Unreachable", "box", "orange"); + + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } + } +}; inline NodeBox::NodeBox() : node(std::make_unique()), /* TODO: avoid allocation of unexplored node */ parent(nullptr) {} +inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { + // fill the current NodeBox with an ifelse branch node it's unexplored + if (dynamic_cast(node.get())) { + node = std::make_unique(cond); + } + assert(dynamic_cast(node.get()) != nullptr && + "Current node is not an IfElseNode, cannot fill it!"); + return std::monostate(); +} + +inline std::monostate NodeBox::fillFinishedNode() { + if (dynamic_cast(node.get())) { + node = std::make_unique(); + } else { + assert(dynamic_cast(node.get()) != nullptr); + } + return std::monostate(); +} + +inline std::monostate NodeBox::fillFailedNode() { + if (dynamic_cast(node.get())) { + node = std::make_unique(); + } else { + assert(dynamic_cast(node.get()) != nullptr); + } + return std::monostate(); +} + +inline std::monostate NodeBox::fillUnreachableNode() { + if (dynamic_cast(node.get())) { + node = std::make_unique(); + } else { + assert(dynamic_cast(node.get()) != nullptr); + } + return std::monostate(); +} + +inline std::vector NodeBox::collect_path_conds() { + auto box = this; + auto result = std::vector(); + while (box->parent) { + auto parent = box->parent; + auto if_else_node = dynamic_cast(parent->node.get()); + if (if_else_node) { + if (if_else_node->true_branch.get() == box) { + // If the current box is the true branch, add the condition + result.push_back(if_else_node->cond); + } else if (if_else_node->false_branch.get() == box) { + // If the current box is the false branch, add the negated condition + result.push_back(if_else_node->cond.negate()); + } else { + throw std::runtime_error("Unexpected node structure in explore tree"); + } + } + // Move to parent + box = box->parent; + } + return result; +} + class ExploreTree_t { public: explicit ExploreTree_t() @@ -351,32 +432,12 @@ class ExploreTree_t { cursor = root.get(); } - std::monostate fillFinishedNode() { - if (dynamic_cast(cursor->node.get())) { - cursor->node = std::make_unique(); - } else { - assert(dynamic_cast(cursor->node.get()) != nullptr); - } - return std::monostate{}; - } + std::monostate fillFinishedNode() { return cursor->fillFinishedNode(); } - std::monostate fillFailedNode() { - if (dynamic_cast(cursor->node.get())) { - cursor->node = std::make_unique(); - } else { - assert(dynamic_cast(cursor->node.get()) != nullptr); - } - return std::monostate{}; - } + std::monostate fillFailedNode() { return cursor->fillFailedNode(); } std::monostate fillIfElseNode(SymVal cond) { - // fill the current NodeBox with an ifelse branch node it's unexplored - if (dynamic_cast(cursor->node.get())) { - cursor->node = std::make_unique(cond); - } - assert(dynamic_cast(cursor->node.get()) != nullptr && - "Current node is not an IfElseNode, cannot fill it!"); - return std::monostate(); + return cursor->fillIfElseNode(cond); } std::monostate moveCursor(bool branch) { @@ -419,24 +480,7 @@ class ExploreTree_t { if (!box) { return std::nullopt; } - while (box->parent) { - auto parent = box->parent; - auto if_else_node = dynamic_cast(parent->node.get()); - if (if_else_node) { - if (if_else_node->true_branch.get() == box) { - // If the current box is the true branch, add the condition - result.push_back(if_else_node->cond); - } else if (if_else_node->false_branch.get() == box) { - // If the current box is the false branch, add the negated condition - result.push_back(if_else_node->cond.negate()); - } else { - throw std::runtime_error("Unexpected node structure in explore tree"); - } - } - // Move to parent - box = box->parent; - } - return result; + return box->collect_path_conds(); } NodeBox *pick_unexplored() { diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 71463bf5e..eb8d3aabb 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -982,7 +982,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "sym-env-read", List(sym), _) => emit("SymEnv.read("); shallow(sym); emit(")") case Node(_, "assert-true", List(cond), _) => - emit("assert("); shallow(cond); emit(")") + emit("GENSYM_ASSERT("); shallow(cond); emit(")") case Node(_, "tree-fill-if-else", List(s), _) => emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") case Node(_, "tree-fill-finished", List(), _) => From b75a627a59c88ac7738b7bf4c8a7944e74b5f6b1 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 19 Jul 2025 13:20:40 +0800 Subject: [PATCH 015/105] call z3 to solve constraints --- headers/wasm/concolic_driver.hpp | 13 ++-- headers/wasm/smt_solver.hpp | 120 ++++++++++++++++++++++++++++--- headers/wasm/symbolic_rt.hpp | 39 ++++++---- 3 files changed, 145 insertions(+), 27 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 9c35f1614..ea28d082c 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -1,11 +1,13 @@ #ifndef CONCOLIC_DRIVER_HPP #define CONCOLIC_DRIVER_HPP +#include "concrete_rt.hpp" #include "smt_solver.hpp" #include "symbolic_rt.hpp" #include #include #include +#include class ConcolicDriver { friend class ManagedConcolicCleanup; @@ -45,16 +47,19 @@ inline void ConcolicDriver::run() { return; } auto cond = unexplored->collect_path_conds(); - auto new_env = solver.solve(cond); - if (!new_env.has_value()) { + std::vector new_env; + std::set valid_ids; + auto result = solver.solve(cond); + if (!result.has_value()) { // TODO: current implementation is buggy, there could be other reachable // unexplored paths std::cout << "Found an unreachable path, marking it as unreachable..." << std::endl; unexplored->fillUnreachableNode(); - continue; + continue; } - SymEnv.update(std::move(new_env.value())); + std::tie(new_env, valid_ids) = std::move(result.value()); + SymEnv.update(std::move(new_env), std::move(valid_ids)); try { entrypoint(); std::cout << "Execution finished successfully with symbolic environment:" diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index a3bbf78d4..8e3f82e40 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -3,26 +3,124 @@ #include "concrete_rt.hpp" #include "symbolic_rt.hpp" +#include "z3++.h" #include +#include +#include +#include #include class Solver { public: - Solver() : count(0) { - envs[0] = {Num(0), Num(0)}; - envs[1] = {Num(1), Num(2)}; - } - std::optional> solve(const std::vector &conditions) { - // here is just a placeholder implementation to simulate solving result - if (count >= envs.size()) { - return std::nullopt; // No more environments to return + Solver() {} + std::optional, std::set>> + solve(const std::vector &conditions) { + // make an conjunction of all conditions + z3::expr conjunction = z3_ctx.bool_val(true); + for (const auto &cond : conditions) { + auto z3_cond = build_z3_expr(cond); + conjunction = conjunction && z3_cond != z3_ctx.bv_val(0, 32); + } +#ifdef DEBUG + std::cout << "Symbolic conditions size: " << conditions.size() << std::endl; + std::cout << "Solving conditions: " << conjunction << std::endl; +#endif + // call z3 to solve the condition + z3::solver z3_solver(z3_ctx); + z3_solver.add(conjunction); + switch (z3_solver.check()) { + case z3::unsat: + return std::nullopt; // No solution found + case z3::sat: { + z3::model model = z3_solver.get_model(); + std::vector result(max_id + 1, Num(0)); + // Reference: + // https://github.com/Z3Prover/z3/blob/master/examples/c%2B%2B/example.cpp#L59 + + std::cout << "Solved Z3 model" << model << std::endl; + std::set seen_ids; + for (unsigned i = 0; i < model.size(); ++i) { + z3::func_decl var = model[i]; + z3::expr value = model.get_const_interp(var); + std::string name = var.name().str(); + if (name.starts_with("s_")) { + int id = std::stoi(name.substr(2)); + seen_ids.insert(id); + result[id] = Num(value.get_numeral_int()); + } else { + std::cout << "Find a variable that is not created by GenSym: " << name + << std::endl; + } + } + return std::make_tuple(result, seen_ids); } - return envs[count++ % envs.size()]; + case z3::unknown: + throw std::runtime_error("Z3 solver returned unknown status"); + } + return std::nullopt; // Should not reach here } private: - std::array, 5> envs; - int count; + z3::context z3_ctx; + z3::expr build_z3_expr(const SymVal &sym_val); }; +inline z3::expr Solver::build_z3_expr(const SymVal &sym_val) { + if (auto sym = std::dynamic_pointer_cast(sym_val.symptr)) { + return z3_ctx.bv_const(("s_" + std::to_string(sym->get_id())).c_str(), 32); + } else if (auto concrete = + std::dynamic_pointer_cast(sym_val.symptr)) { + return z3_ctx.bv_val(concrete->value.value, 32); + } else if (auto binary = + std::dynamic_pointer_cast(sym_val.symptr)) { + auto bit_width = 32; + z3::expr zero_bv = + z3_ctx.bv_val(0, bit_width); // Represents 0 as a 32-bit bitvector + z3::expr one_bv = + z3_ctx.bv_val(1, bit_width); // Represents 1 as a 32-bit bitvector + + z3::expr left = build_z3_expr(binary->lhs); + z3::expr right = build_z3_expr(binary->rhs); + // TODO: make sure the semantics of these operations are aligned with wasm + switch (binary->op) { + case EQ: { + auto temp_bool = left == right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case NEQ: { + auto temp_bool = left != right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case LT: { + auto temp_bool = left < right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case LEQ: { + auto temp_bool = left <= right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case GT: { + auto temp_bool = left > right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case GEQ: { + auto temp_bool = left >= right; + return z3::ite(temp_bool, one_bv, zero_bv); + } + case ADD: { + return left + right; + } + case SUB: { + return left - right; + } + case MUL: { + return left * right; + } + case DIV: { + return left / right; + } + } + } + throw std::runtime_error("Unsupported symbolic value type"); +} #endif // SMT_SOLVER_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 95f292b55..3e7ea2cc4 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -9,6 +9,7 @@ #include #include #include +#include #include #include #include @@ -19,9 +20,13 @@ class Symbolic { virtual ~Symbolic() = default; // Make Symbolic polymorphic }; +static int max_id = 0; + class Symbol : public Symbolic { public: - Symbol(int id) : id(id) {} + // TODO: add type information to determine the size of bitvector + // for now we just assume that only i32 will be used + Symbol(int id) : id(id) { max_id = std::max(max_id, id); } int get_id() const { return id; } private: @@ -190,7 +195,7 @@ static SymFrames_t SymFrames; struct Node; struct NodeBox { - explicit NodeBox(); + explicit NodeBox(NodeBox *parent); std::unique_ptr node; NodeBox *parent; @@ -247,9 +252,9 @@ struct IfElseNode : Node { std::unique_ptr true_branch; std::unique_ptr false_branch; - IfElseNode(SymVal cond) - : cond(cond), true_branch(std::make_unique()), - false_branch(std::make_unique()) {} + IfElseNode(SymVal cond, NodeBox *parent) + : cond(cond), true_branch(std::make_unique(parent)), + false_branch(std::make_unique(parent)) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -357,15 +362,15 @@ struct Unreachable : Node { } }; -inline NodeBox::NodeBox() +inline NodeBox::NodeBox(NodeBox *parent) : node(std::make_unique()), /* TODO: avoid allocation of unexplored node */ - parent(nullptr) {} + parent(parent) {} inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { // fill the current NodeBox with an ifelse branch node it's unexplored if (dynamic_cast(node.get())) { - node = std::make_unique(cond); + node = std::make_unique(cond, this); } assert(dynamic_cast(node.get()) != nullptr && "Current node is not an IfElseNode, cannot fill it!"); @@ -425,7 +430,7 @@ inline std::vector NodeBox::collect_path_conds() { class ExploreTree_t { public: explicit ExploreTree_t() - : root(std::make_unique()), cursor(root.get()) {} + : root(std::make_unique(nullptr)), cursor(root.get()) {} void reset_cursor() { // Reset the cursor to the root of the tree @@ -513,13 +518,22 @@ static ExploreTree_t ExploreTree; class SymEnv_t { public: Num read(SymVal sym) { - return Num(0); auto symbol = dynamic_cast(sym.symptr.get()); assert(symbol); + if (symbol->get_id() >= map.size()) { + map.resize(symbol->get_id() + 1); + } +#if DEBUG + std::cout << "Read symbol: " << symbol->get_id() + << " from symbolic environment" << std::endl; + std::cout << "Current symbolic environment: " << to_string() << std::endl; +#endif return map[symbol->get_id()]; } - void update(std::vector new_env) { map = std::move(new_env); } + void update(std::vector new_env, std::set valid_ids) { + map = std::move(new_env); + } std::string to_string() const { std::string result; @@ -534,7 +548,8 @@ class SymEnv_t { } private: - std::vector map; // The symbolic environment, a vector of Num + std::vector map; // The symbolic environment, a vector of Num + std::set valid_ids; // The set of valid IDs in the symbolic environment }; static SymEnv_t SymEnv; From 26c9917fcb39e84f33318955fb3a9b3a3fd9fb32 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 19 Jul 2025 17:48:20 +0800 Subject: [PATCH 016/105] remove unused & resize before update environment --- headers/wasm/concolic_driver.hpp | 6 ++---- headers/wasm/smt_solver.hpp | 14 +++++++------- headers/wasm/symbolic_rt.hpp | 3 +-- 3 files changed, 10 insertions(+), 13 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index ea28d082c..8e8ca815b 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -47,8 +47,6 @@ inline void ConcolicDriver::run() { return; } auto cond = unexplored->collect_path_conds(); - std::vector new_env; - std::set valid_ids; auto result = solver.solve(cond); if (!result.has_value()) { // TODO: current implementation is buggy, there could be other reachable @@ -58,8 +56,8 @@ inline void ConcolicDriver::run() { unexplored->fillUnreachableNode(); continue; } - std::tie(new_env, valid_ids) = std::move(result.value()); - SymEnv.update(std::move(new_env), std::move(valid_ids)); + auto new_env = result.value(); + SymEnv.update(std::move(new_env)); try { entrypoint(); std::cout << "Execution finished successfully with symbolic environment:" diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 8e3f82e40..de5b80cbe 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -13,8 +13,7 @@ class Solver { public: Solver() {} - std::optional, std::set>> - solve(const std::vector &conditions) { + std::optional> solve(const std::vector &conditions) { // make an conjunction of all conditions z3::expr conjunction = z3_ctx.bool_val(true); for (const auto &cond : conditions) { @@ -33,26 +32,27 @@ class Solver { return std::nullopt; // No solution found case z3::sat: { z3::model model = z3_solver.get_model(); - std::vector result(max_id + 1, Num(0)); + std::vector result; // Reference: // https://github.com/Z3Prover/z3/blob/master/examples/c%2B%2B/example.cpp#L59 - std::cout << "Solved Z3 model" << model << std::endl; - std::set seen_ids; + std::cout << "Solved Z3 model" << std::endl << model << std::endl; for (unsigned i = 0; i < model.size(); ++i) { z3::func_decl var = model[i]; z3::expr value = model.get_const_interp(var); std::string name = var.name().str(); if (name.starts_with("s_")) { int id = std::stoi(name.substr(2)); - seen_ids.insert(id); + if (id >= result.size()) { + result.resize(id + 1); + } result[id] = Num(value.get_numeral_int()); } else { std::cout << "Find a variable that is not created by GenSym: " << name << std::endl; } } - return std::make_tuple(result, seen_ids); + return result; } case z3::unknown: throw std::runtime_error("Z3 solver returned unknown status"); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 3e7ea2cc4..18629c804 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -531,7 +531,7 @@ class SymEnv_t { return map[symbol->get_id()]; } - void update(std::vector new_env, std::set valid_ids) { + void update(std::vector new_env) { map = std::move(new_env); } @@ -549,7 +549,6 @@ class SymEnv_t { private: std::vector map; // The symbolic environment, a vector of Num - std::set valid_ids; // The set of valid IDs in the symbolic environment }; static SymEnv_t SymEnv; From 319cfd6576f0399bcfdd3668e0a19b9feeadcad2 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 23 Jul 2025 14:11:42 +0800 Subject: [PATCH 017/105] use c++20 --- src/main/scala/wasm/StagedConcolicMiniWasm.scala | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index eb8d3aabb..922d2113e 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -1080,7 +1080,7 @@ object WasmToCppCompiler { } import sys.process._ - val command = s"g++ -std=c++17 $outputCpp -o $outputExe -O3 -g " + generated.headerFolders.map(f => s"-I$f").mkString(" ") + val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g " + generated.headerFolders.map(f => s"-I$f").mkString(" ") if (command.! != 0) { throw new RuntimeException(s"Compilation failed for $outputCpp") } From 8f45912f6275c9dc5a5ee8bab34b02bcae3b5609 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 23 Jul 2025 19:28:50 +0800 Subject: [PATCH 018/105] branch in brtable --- benchmarks/wasm/staged/brtable_concolic.wat | 22 +++++++++++++++++++ headers/wasm/smt_solver.hpp | 2 +- .../scala/wasm/StagedConcolicMiniWasm.scala | 17 +++++++++++--- .../genwasym/TestStagedConcolicEval.scala | 4 ++++ 4 files changed, 41 insertions(+), 4 deletions(-) create mode 100644 benchmarks/wasm/staged/brtable_concolic.wat diff --git a/benchmarks/wasm/staged/brtable_concolic.wat b/benchmarks/wasm/staged/brtable_concolic.wat new file mode 100644 index 000000000..04429e90b --- /dev/null +++ b/benchmarks/wasm/staged/brtable_concolic.wat @@ -0,0 +1,22 @@ +(module $brtable + (global (;0;) (mut i32) (i32.const 1048576)) + (type (;0;) (func (param i32))) + (func (;0;) (type 1) (result i32) + i32.const 2 + (block + (block + (block + i32.const 0 + i32.symbolic + br_table 0 1 2 0 ;; br_table will consume an element from the stack + ) + i32.const 1 + call 1 + br 1 + ) + i32.const 0 + call 1 + ) + ) + (import "console" "assert" (func (type 0))) + (start 0)) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index de5b80cbe..f24509050 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -46,7 +46,7 @@ class Solver { if (id >= result.size()) { result.resize(id + 1); } - result[id] = Num(value.get_numeral_int()); + result[id] = Num(value.get_numeral_int64()); } else { std::cout << "Find a variable that is not created by GenSym: " << name << std::endl; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 922d2113e..6c8e45aa9 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -17,6 +17,7 @@ import gensym.wasm.symbolic.{SymVal} import gensym.lmsx.{SAIDriver, StringOps, SAIOps, SAICodeGenBase, CppSAIDriver, CppSAICodeGenBase} import gensym.wasm.symbolic.Concrete import gensym.wasm.symbolic.ExploreTree +import gensym.structure.freer.Explore @virtualize trait StagedWasmEvaluator extends SAIOps { @@ -270,12 +271,20 @@ trait StagedWasmEvaluator extends SAIOps { } () case BrTable(labels, default) => - val (cond, newCtx) = Stack.pop() + val (label, newCtx) = Stack.pop() def aux(choices: List[Int], idx: Int): Rep[Unit] = { if (choices.isEmpty) trail(default)(newCtx)(mkont) else { - if (cond.toInt == idx) trail(choices.head)(newCtx)(mkont) - else aux(choices.tail, idx + 1) + val cond = (label - toStagedNum(I32V(idx))).isZero() + ExploreTree.fillWithIfElse(cond.s) + if (cond.toInt != 0) { + ExploreTree.moveCursor(true) + trail(choices.head)(newCtx)(mkont) + } + else { + ExploreTree.moveCursor(false) + aux(choices.tail, idx + 1) + } } } aux(labels, 0) @@ -959,6 +968,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(" >= "); shallow(rhs) case Node(_, "sym-binary-add", List(lhs, rhs), _) => shallow(lhs); emit(".add("); shallow(rhs); emit(")") + case Node(_, "sym-binary-sub", List(lhs, rhs), _) => + shallow(lhs); emit(".minus("); shallow(rhs); emit(")") case Node(_, "sym-binary-mul", List(lhs, rhs), _) => shallow(lhs); emit(".mul("); shallow(rhs); emit(")") case Node(_, "sym-binary-div", List(lhs, rhs), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 77868e2c2..fa7f704b2 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -35,4 +35,8 @@ class TestStagedConcolicEval extends FunSuite { test("bug-finding") { testFileToCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) } + + test("brtable-bug-finding") { + testFileToCpp("./benchmarks/wasm/staged/brtable_concolic.wat") + } } From 2e2259d0bbd18aa122d201d62bc03d245c6ec191 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 23 Jul 2025 19:32:49 +0800 Subject: [PATCH 019/105] use driver's entrypoint by default --- src/main/scala/wasm/StagedConcolicMiniWasm.scala | 4 ++-- src/test/scala/genwasym/TestStagedConcolicEval.scala | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 6c8e45aa9..833bbc9b8 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -1047,7 +1047,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { |End of Generated Code |*******************************************/ |int main(int argc, char *argv[]) { - | Snippet(std::monostate{}); + | start_concolic_execution_with(Snippet); | return 0; |}""".stripMargin) } @@ -1091,7 +1091,7 @@ object WasmToCppCompiler { } import sys.process._ - val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g " + generated.headerFolders.map(f => s"-I$f").mkString(" ") + val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g -l z3 " + generated.headerFolders.map(f => s"-I$f").mkString(" ") if (command.! != 0) { throw new RuntimeException(s"Compilation failed for $outputCpp") } diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index fa7f704b2..a65d0edad 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -30,7 +30,7 @@ class TestStagedConcolicEval extends FunSuite { }) } - test("ack-cpp") { testFileToCpp("./benchmarks/wasm/ack.wat", Some("real_main"), expect=Some(List(7))) } + test("ack-cpp") { testFileToCpp("./benchmarks/wasm/ack.wat", Some("real_main")) } test("bug-finding") { testFileToCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) From 2b42b277cfa42e6d06ba49f70daba327c4c4abcf Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 23 Jul 2025 20:09:12 +0800 Subject: [PATCH 020/105] rename package name of staged miniwasm --- src/main/scala/wasm/StagedMiniWasm.scala | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/main/scala/wasm/StagedMiniWasm.scala b/src/main/scala/wasm/StagedMiniWasm.scala index bfa2082d1..ea9dc9c6f 100644 --- a/src/main/scala/wasm/StagedMiniWasm.scala +++ b/src/main/scala/wasm/StagedMiniWasm.scala @@ -1,4 +1,4 @@ -package gensym.wasm.miniwasm +package gensym.wasm.stagedminiwasm import scala.collection.mutable.{ArrayBuffer, HashMap} @@ -12,6 +12,7 @@ import lms.core.Graph import gensym.wasm.ast._ import gensym.wasm.ast.{Const => WasmConst, Block => WasmBlock} +import gensym.wasm.miniwasm.ModuleInstance import gensym.lmsx.{SAIDriver, StringOps, SAIOps, SAICodeGenBase, CppSAIDriver, CppSAICodeGenBase} @virtualize From 619a8f022d015d67ccbc4919bc49801175dc9dda Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 23 Jul 2025 20:15:29 +0800 Subject: [PATCH 021/105] tweak --- src/test/scala/genwasym/TestStagedEval.scala | 1 + 1 file changed, 1 insertion(+) diff --git a/src/test/scala/genwasym/TestStagedEval.scala b/src/test/scala/genwasym/TestStagedEval.scala index d4d1e960f..3769428f4 100644 --- a/src/test/scala/genwasym/TestStagedEval.scala +++ b/src/test/scala/genwasym/TestStagedEval.scala @@ -6,6 +6,7 @@ import lms.core.stub.Adapter import gensym.wasm.parser._ import gensym.wasm.miniwasm._ +import gensym.wasm.stagedminiwasm._ class TestStagedEval extends FunSuite { def testFileToScala(filename: String, main: Option[String] = None, printRes: Boolean = false) = { From af6751aca613e013efc78e751b0dd1a4e0b420e6 Mon Sep 17 00:00:00 2001 From: butterunderflow <112108686+butterunderflow@users.noreply.github.com> Date: Wed, 27 Aug 2025 19:09:08 -0400 Subject: [PATCH 022/105] Reuse symbolic states (#90) 1. split concrete and symbolic interpreter 2. copy tests from concrete execution 3. some bug fixes --- benchmarks/wasm/staged/return_poly.wat | 19 + headers/wasm/concolic_driver.hpp | 23 +- headers/wasm/concrete_rt.hpp | 6 +- headers/wasm/controls.hpp | 5 + headers/wasm/smt_solver.hpp | 8 +- headers/wasm/symbolic_rt.hpp | 146 +- headers/wasm/utils.hpp | 24 + .../scala/wasm/StagedConcolicMiniWasm.scala | 1234 +++++++++++++---- .../genwasym/TestStagedConcolicEval.scala | 70 +- 9 files changed, 1198 insertions(+), 337 deletions(-) create mode 100644 benchmarks/wasm/staged/return_poly.wat create mode 100644 headers/wasm/controls.hpp diff --git a/benchmarks/wasm/staged/return_poly.wat b/benchmarks/wasm/staged/return_poly.wat new file mode 100644 index 000000000..1bab5ef0f --- /dev/null +++ b/benchmarks/wasm/staged/return_poly.wat @@ -0,0 +1,19 @@ +(module + (type (;0;) (func)) + (type (;1;) (func (result i32))) + ;; TODO: It seems that our parser or preprocessor has some problems; the result type of the last line doesn't take effect + (func (result i32) + block + i32.const 21 + i32.const 35 + i32.const 42 + return + end + i32.const 100 + ) + (func (type 0) + call 0 + ;; unreachable + ) + (export "$real_main" (func 1)) +) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 8e8ca815b..427a0de83 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -4,6 +4,7 @@ #include "concrete_rt.hpp" #include "smt_solver.hpp" #include "symbolic_rt.hpp" +#include "utils.hpp" #include #include #include @@ -43,33 +44,33 @@ inline void ConcolicDriver::run() { auto unexplored = ExploreTree.pick_unexplored(); if (!unexplored) { - std::cout << "No unexplored nodes found, exiting..." << std::endl; + GENSYM_INFO("No unexplored nodes found, exiting..."); return; } auto cond = unexplored->collect_path_conds(); auto result = solver.solve(cond); if (!result.has_value()) { - // TODO: current implementation is buggy, there could be other reachable - // unexplored paths - std::cout << "Found an unreachable path, marking it as unreachable..." - << std::endl; + GENSYM_INFO("Found an unreachable path, marking it as unreachable..."); unexplored->fillUnreachableNode(); continue; } auto new_env = result.value(); SymEnv.update(std::move(new_env)); try { + GENSYM_INFO("Now execute the program with symbolic environment: "); + GENSYM_INFO(SymEnv.to_string()); entrypoint(); - std::cout << "Execution finished successfully with symbolic environment:" - << std::endl; - std::cout << SymEnv.to_string() << std::endl; + GENSYM_INFO("Execution finished successfully with symbolic environment:"); + GENSYM_INFO(SymEnv.to_string()); } catch (...) { ExploreTree.fillFailedNode(); - std::cout << "Caught runtime error with symbolic environment:" - << std::endl; - std::cout << SymEnv.to_string() << std::endl; + GENSYM_INFO("Caught runtime error with symbolic environment:"); + GENSYM_INFO(SymEnv.to_string()); return; } +#if defined(RUN_ONCE) + return; +#endif } } diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index a09614537..a9abccf2d 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -72,9 +72,7 @@ class Stack_t { Num pop() { #ifdef DEBUG - if (count == 0) { - throw std::runtime_error("Stack underflow"); - } + assert(count > 0 && "Stack underflow"); #endif Num num = stack_ptr[count - 1]; count--; @@ -117,7 +115,7 @@ class Stack_t { void initialize() { // todo: remove this method - reset(); + reset(); } void reset() { count = 0; } diff --git a/headers/wasm/controls.hpp b/headers/wasm/controls.hpp new file mode 100644 index 000000000..16fa5136a --- /dev/null +++ b/headers/wasm/controls.hpp @@ -0,0 +1,5 @@ +#include +#include + +using MCont_t = std::function; +using Cont_t = std::function; \ No newline at end of file diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index f24509050..bc8cc9f94 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -3,6 +3,7 @@ #include "concrete_rt.hpp" #include "symbolic_rt.hpp" +#include "utils.hpp" #include "z3++.h" #include #include @@ -35,8 +36,8 @@ class Solver { std::vector result; // Reference: // https://github.com/Z3Prover/z3/blob/master/examples/c%2B%2B/example.cpp#L59 - - std::cout << "Solved Z3 model" << std::endl << model << std::endl; + GENSYM_INFO("Solved Z3 model"); + GENSYM_INFO(model); for (unsigned i = 0; i < model.size(); ++i) { z3::func_decl var = model[i]; z3::expr value = model.get_const_interp(var); @@ -48,8 +49,7 @@ class Solver { } result[id] = Num(value.get_numeral_int64()); } else { - std::cout << "Find a variable that is not created by GenSym: " << name - << std::endl; + GENSYM_INFO("Find a variable that is not created by GenSym: " + name); } } return result; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 18629c804..94351f077 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -2,7 +2,9 @@ #define WASM_SYMBOLIC_RT_HPP #include "concrete_rt.hpp" +#include "controls.hpp" #include +#include #include #include #include @@ -22,6 +24,12 @@ class Symbolic { static int max_id = 0; +#ifdef NO_REUSE +static bool REUSE_MODE = false; +#else +static bool REUSE_MODE = true; +#endif + class Symbol : public Symbolic { public: // TODO: add type information to determine the size of bitvector @@ -65,6 +73,10 @@ struct SymVal { SymVal negate() const; }; +static SymVal make_symbolic(int index) { + return SymVal(std::make_shared(index)); +} + inline SymVal Concrete(Num num) { return SymVal(std::make_shared(num)); } @@ -133,6 +145,8 @@ inline SymVal SymVal::makeSymbolic() const { } } +class Snapshot_t; + class SymStack_t { public: void push(SymVal val) { @@ -142,6 +156,11 @@ class SymStack_t { SymVal pop() { // Pop a symbolic value from the stack + +#ifdef DEBUG + printf("[Debug] poping from stack, size of symbolic stack is: %zu\n", + stack.size()); +#endif auto ret = stack.back(); stack.pop_back(); return ret; @@ -149,11 +168,25 @@ class SymStack_t { SymVal peek() { return stack.back(); } + std::monostate shift(int32_t offset, int32_t size) { + auto n = stack.size(); + for (size_t i = n - size; i < n; ++i) { + stack[i - offset] = stack[i]; + } + stack.resize(n - offset); + return std::monostate(); + } + void reset() { // Reset the symbolic stack stack.clear(); } + void reuse(Snapshot_t snapshot); + + size_t size() const { return stack.size(); } + +private: std::vector stack; }; @@ -187,9 +220,46 @@ class SymFrames_t { stack.clear(); } + void reuse(Snapshot_t snapshot); + std::vector stack; }; +// A snapshot of the symbolic state and execution context (control) +class Snapshot_t { +public: + explicit Snapshot_t(); + + SymStack_t get_stack() const { return stack; } + SymFrames_t get_frames() const { return frames; } + +private: + SymStack_t stack; + SymFrames_t frames; +}; + +inline void SymStack_t::reuse(Snapshot_t snapshot) { +// Reusing the symbolic stack from the snapshot +#ifdef DEBUG + std::cout << "Reusing symbolic state from snapshot" << std::endl; + std::cout << "Old stack size = " << stack.size() << std::endl; + std::cout << "New stack size = " << snapshot.get_stack().stack.size() + << std::endl; +#endif + stack = snapshot.get_stack().stack; +} + +inline void SymFrames_t::reuse(Snapshot_t snapshot) { +// Reusing the symbolic frames from the snapshot +#ifdef DEBUG + std::cout << "Reusing symbolic state from snapshot" << std::endl; + std::cout << "Old frame size = " << stack.size() << std::endl; + std::cout << "New frame size = " << snapshot.get_frames().stack.size() + << std::endl; +#endif + stack = snapshot.get_frames().stack; +} + static SymFrames_t SymFrames; struct Node; @@ -199,7 +269,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond); + std::monostate fillIfElseNode(SymVal cond, const Snapshot_t &snapshot); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -251,8 +321,9 @@ struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; + Snapshot_t snapshot; - IfElseNode(SymVal cond, NodeBox *parent) + IfElseNode(SymVal cond, NodeBox *parent, Snapshot_t snapshot) : cond(cond), true_branch(std::make_unique(parent)), false_branch(std::make_unique(parent)) {} @@ -367,13 +438,15 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { - // fill the current NodeBox with an ifelse branch node it's unexplored +inline std::monostate NodeBox::fillIfElseNode(SymVal cond, + const Snapshot_t &snapshot) { + // fill the current NodeBox with an ifelse branch node when it's unexplored if (dynamic_cast(node.get())) { - node = std::make_unique(cond, this); + node = std::make_unique(cond, this, snapshot); } - assert(dynamic_cast(node.get()) != nullptr && - "Current node is not an IfElseNode, cannot fill it!"); + assert( + dynamic_cast(node.get()) != nullptr && + "Current node is not an Unexplored nor an IfElseNode, cannot fill it!"); return std::monostate(); } @@ -427,6 +500,32 @@ inline std::vector NodeBox::collect_path_conds() { return result; } +class Reuse_t { +public: + Reuse_t() : reuse_flag(false) {} + bool is_reusing() { + // we are in reuse mode and the flag is set + return REUSE_MODE && reuse_flag; + } + + void turn_on_reusing() { reuse_flag = true; } + + void turn_off_reusing() { reuse_flag = false; } + +private: + bool reuse_flag; +}; + +static Reuse_t Reuse; + +inline Snapshot_t::Snapshot_t() : stack(SymStack), frames(SymFrames) { +#ifdef DEBUG + std::cout << "Creating snapshot of size " << stack.size() << std::endl; +#endif + assert(!Reuse.is_reusing() && + "Creating snapshot while reusing the symbolic stack"); +} + class ExploreTree_t { public: explicit ExploreTree_t() @@ -435,14 +534,19 @@ class ExploreTree_t { void reset_cursor() { // Reset the cursor to the root of the tree cursor = root.get(); + Reuse.turn_off_reusing(); + // if root cursor is a branch node, then we can reuse the snapshot inside it + if (auto ite = dynamic_cast(cursor->node.get())) { + Reuse.turn_on_reusing(); + } } std::monostate fillFinishedNode() { return cursor->fillFinishedNode(); } std::monostate fillFailedNode() { return cursor->fillFailedNode(); } - std::monostate fillIfElseNode(SymVal cond) { - return cursor->fillIfElseNode(cond); + std::monostate fillIfElseNode(SymVal cond, const Snapshot_t &snapshot) { + return cursor->fillIfElseNode(cond, snapshot); } std::monostate moveCursor(bool branch) { @@ -456,6 +560,24 @@ class ExploreTree_t { } else { cursor = if_else_node->false_branch.get(); } + + if (dynamic_cast(cursor->node.get())) { + // If we meet an unexplored node, resume the snapshot before and keep + // going + +#ifdef DEBUG + std::cout << "Resuming snapshot for unexplored node" << std::endl; +#endif + if (Reuse.is_reusing()) { + Reuse.turn_off_reusing(); + SymStack.reuse(if_else_node->snapshot); + } + } else if (dynamic_cast(cursor->node.get())) { + // if we are moving to a branch node, we must have reused the symbolic + // states + assert((!REUSE_MODE || Reuse.is_reusing()) && + "Moving to a branch node without reusing symbolic states"); + } return std::monostate(); } @@ -531,9 +653,7 @@ class SymEnv_t { return map[symbol->get_id()]; } - void update(std::vector new_env) { - map = std::move(new_env); - } + void update(std::vector new_env) { map = std::move(new_env); } std::string to_string() const { std::string result; @@ -548,7 +668,7 @@ class SymEnv_t { } private: - std::vector map; // The symbolic environment, a vector of Num + std::vector map; // The symbolic environment, a vector of Num }; static SymEnv_t SymEnv; diff --git a/headers/wasm/utils.hpp b/headers/wasm/utils.hpp index 8a86ac98d..ba57a1df0 100644 --- a/headers/wasm/utils.hpp +++ b/headers/wasm/utils.hpp @@ -12,4 +12,28 @@ } while (0) #endif +#ifndef NO_DBG +#define GENSYM_DBG(obj) \ + do { \ + std::cout << "LOG: " << obj << " (" << __FILE__ << ":" \ + << std::to_string(__LINE__) << ")" << std::endl; \ + } while (0) +#else +#define GENSYM_LOG(message) \ + do { \ + } while (0) +#endif + +#ifndef NO_INFO +#define GENSYM_INFO(obj) \ + do { \ + std::cout << obj << std::endl; \ + } while (0) +#else +#define GENSYM_INFO(message) \ + do { \ + } while (0) + +#endif + #endif // UTILS_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 833bbc9b8..769a0b85e 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -26,28 +26,57 @@ trait StagedWasmEvaluator extends SAIOps { trait ReturnSite trait StagedNum { + def tipe: ValueType + } + + trait StagedConcreteNum { def tipe: ValueType = this match { - case I32(_, _) => NumType(I32Type) - case I64(_, _) => NumType(I64Type) - case F32(_, _) => NumType(F32Type) - case F64(_, _) => NumType(F64Type) + case I32C(_) => NumType(I32Type) + case I64C(_) => NumType(I64Type) + case F32C(_) => NumType(F32Type) + case F64C(_) => NumType(F64Type) } def i: Rep[Num] + } + + case class I32C(i: Rep[Num]) extends StagedConcreteNum + case class I64C(i: Rep[Num]) extends StagedConcreteNum + case class F32C(i: Rep[Num]) extends StagedConcreteNum + case class F64C(i: Rep[Num]) extends StagedConcreteNum + + + trait StagedSymbolicNum { + def tipe: ValueType = this match { + case I32S(_) => NumType(I32Type) + case I64S(_) => NumType(I64Type) + case F32S(_) => NumType(F32Type) + case F64S(_) => NumType(F64Type) + } def s: Rep[SymVal] } - case class I32(i: Rep[Num], s: Rep[SymVal]) extends StagedNum - case class I64(i: Rep[Num], s: Rep[SymVal]) extends StagedNum - case class F32(i: Rep[Num], s: Rep[SymVal]) extends StagedNum - case class F64(i: Rep[Num], s: Rep[SymVal]) extends StagedNum - def toStagedNum(num: Num): StagedNum = { + case class I32S(s: Rep[SymVal]) extends StagedSymbolicNum + case class I64S(s: Rep[SymVal]) extends StagedSymbolicNum + case class F32S(s: Rep[SymVal]) extends StagedSymbolicNum + case class F64S(s: Rep[SymVal]) extends StagedSymbolicNum + + def toStagedNum(num: Num): StagedConcreteNum = { num match { - case I32V(_) => I32(num, Concrete(num)) - case I64V(_) => I64(num, Concrete(num)) - case F32V(_) => F32(num, Concrete(num)) - case F64V(_) => F64(num, Concrete(num)) + case I32V(_) => I32C(num) + case I64V(_) => I64C(num) + case F32V(_) => F32C(num) + case F64V(_) => F64C(num) + } + } + + def toStagedSymbolicNum(num: Num): StagedSymbolicNum = { + num match { + case I32V(_) => I32S(Concrete(num)) + case I64V(_) => I64S(Concrete(num)) + case F32V(_) => F32S(Concrete(num)) + case F64V(_) => F64S(Concrete(num)) } } @@ -59,12 +88,21 @@ trait StagedWasmEvaluator extends SAIOps { case NumType(F64Type) => 8 } - def toTagger: (Rep[Num], Rep[SymVal]) => StagedNum = { + def concreteTag: (Rep[Num]) => StagedConcreteNum = { + ty match { + case NumType(I32Type) => I32C + case NumType(I64Type) => I64C + case NumType(F32Type) => F32C + case NumType(F64Type) => F64C + } + } + + def symbolicTag: (Rep[SymVal]) => StagedSymbolicNum = { ty match { - case NumType(I32Type) => I32 - case NumType(I64Type) => I64 - case NumType(F32Type) => F32 - case NumType(F64Type) => F64 + case NumType(I32Type) => I32S + case NumType(I64Type) => I64S + case NumType(F32Type) => F32S + case NumType(F64Type) => F64S } } } @@ -74,12 +112,22 @@ trait StagedWasmEvaluator extends SAIOps { frameTypes: List[ValueType] ) { def push(ty: ValueType): Context = { - Context(ty :: stackTypes, frameTypes) + this.copy(stackTypes = ty :: stackTypes) + } + + def peek: ValueType = { + stackTypes.head } def pop(): (ValueType, Context) = { val (ty :: rest) = stackTypes - (ty, Context(rest, frameTypes)) + (ty, this.copy(stackTypes = rest)) + } + + def take(n: Int): Context = { + Predef.assert(n <= stackTypes.size, s"Context.take size $n is larger than stack size ${stackTypes.size}") + val (taken, rest) = stackTypes.splitAt(n) + this.copy(stackTypes = rest) } def shift(offset: Int, size: Int): Context = { @@ -93,11 +141,50 @@ trait StagedWasmEvaluator extends SAIOps { ) } } + + } + + case class ContextTransition(startCtx: Context, history: List[Instr], endCtx: Context) { + def log(instr: Instr): ContextTransition = { + this.copy(history = instr :: history) + } + + def clearHistory: (Context, List[Instr], CleanCT) = { + (startCtx, history, CleanCT(endCtx)) + } + + def push(ty: ValueType): ContextTransition = { + this.copy(endCtx = endCtx.push(ty)) + } + + def peek: ValueType = { + endCtx.peek + } + + def pop(): (ValueType, ContextTransition) = { + val (ty, newCtx) = endCtx.pop() + (ty, this.copy(endCtx = newCtx)) + } + + def take(n: Int): ContextTransition = { + this.copy(endCtx = endCtx.take(n)) + } + + def shift(offset: Int, size: Int): ContextTransition = { + this.copy(endCtx = endCtx.shift(offset, size)) + } + } + + case class CleanCT(ctx: Context) + + // we can treat every CleanCT as a ContextTransition + implicit def toContextCT(ct: CleanCT): ContextTransition = { + ContextTransition(ct.ctx, Nil, ct.ctx) } type MCont[A] = Unit => A type Cont[A] = (MCont[A]) => A - type Trail[A] = List[Context => Rep[Cont[A]]] + type Trail[A] = List[CleanCT => Rep[Cont[A]]] // a cache storing the compiled code for each function, to reduce re-compilation val compileCache = new HashMap[Int, Rep[(MCont[Unit]) => Unit]] @@ -113,173 +200,268 @@ trait StagedWasmEvaluator extends SAIOps { } + // TODO: maybe we don't need concern snapshot at compile time at all + trait Snapshot + + // Create a snapshot of the symbolic execution, we should ensure that current symstack is in use + // We don't need to store the control information, since the control is totally decided by concrete states + def makeSnapshot(): Rep[Snapshot] = { + "snapshot-make".reflectCtrlWith[Snapshot]() + } + + def isSymStateInUse: Rep[Boolean] = !ReuseManager.isReusing + def eval(insts: List[Instr], - kont: Context => Rep[Cont[Unit]], + kont: CleanCT => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], trail: Trail[Unit]) - (implicit ctx: Context): Rep[Unit] = { - if (insts.isEmpty) return kont(ctx)(mkont) + (oldCT: ContextTransition): Rep[Unit] = { + if (insts.isEmpty) { + val (oldCtx, history, ct) = oldCT.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + return kont(ct)(mkont) + } // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") // Predef.println(s"[DEBUG] Current context: $ctx") - val (inst, rest) = (insts.head, insts.tail) + val ct = oldCT.log(inst) inst match { case Drop => - val (_, newCtx) = Stack.pop() - eval(rest, kont, mkont, trail)(newCtx) + val (ty, ct1) = ct.pop() + Stack.popC(ty) + eval(rest, kont, mkont, trail)(ct1) case WasmConst(num) => - val newCtx = Stack.push(toStagedNum(num)) - eval(rest, kont, mkont, trail)(newCtx) + Stack.pushC(toStagedNum(num)) + val ct1 = ct.push(num.tipe(module)) + eval(rest, kont, mkont, trail)(ct1) case Symbolic(ty) => - val (id, newCtx1) = Stack.pop() - val symVal = id.makeSymbolic() - val concVal = SymEnv.read(symVal) - val tagger = ty.toTagger - val value = tagger(concVal, symVal) - val newCtx2 = Stack.push(value)(newCtx1) - eval(rest, kont, mkont, trail)(newCtx2) + val id = Stack.popC(ty) + val symVal = id.makeSymbolic(ty) + val num = SymEnv.read(symVal.s) + Stack.pushC(ty.concreteTag(num)) + val ct1 = ct.pop()._2.push(ty) + eval(rest, kont, mkont, trail)(ct1) case LocalGet(i) => - val newCtx = Stack.push(Frames.get(i)) - eval(rest, kont, mkont, trail)(newCtx) + Stack.pushC(Frames.getC(i)(ct.endCtx)) + val ct1 = ct.push(ct.endCtx.frameTypes(i)) + eval(rest, kont, mkont, trail)(ct1) case LocalSet(i) => - val (num, newCtx) = Stack.pop() - Frames.set(i, num)(newCtx) - eval(rest, kont, mkont, trail)(newCtx) + val (ty, ct1) = ct.pop() + val num = Stack.popC(ty) + Frames.setC(i, num) + eval(rest, kont, mkont, trail)(ct1) case LocalTee(i) => - val (num, newCtx) = Stack.peek - Frames.set(i, num) - eval(rest, kont, mkont, trail)(newCtx) + val ty = ct.peek + val num = Stack.peekC(ty) + Frames.setC(i, num) + eval(rest, kont, mkont, trail)(ct) case GlobalGet(i) => - val newCtx = Stack.push(Globals(i)) - eval(rest, kont, mkont, trail)(newCtx) + Stack.pushC(Globals.getC(i)) + val ct1 = ct.push(module.globals(i).ty.ty) + eval(rest, kont, mkont, trail)(ct1) case GlobalSet(i) => - val (value, newCtx) = Stack.pop() + val (ty, ct1) = ct.pop() + val num = Stack.popC(ty) module.globals(i).ty match { - case GlobalType(tipe, true) => Globals(i) = value + case GlobalType(tipe, true) => { + Globals.setC(i, num) + } case _ => throw new Exception("Cannot set immutable global") } - eval(rest, kont, mkont, trail)(newCtx) + eval(rest, kont, mkont, trail)(ct1) case Store(StoreOp(align, offset, ty, None)) => - val (value, newCtx1) = Stack.pop() - val (addr, newCtx2) = Stack.pop()(newCtx1) + val (ty1, ct1) = ct.pop() + val value = Stack.popC(ty1) + val (ty2, ct2) = ct1.pop() + val addr = Stack.popC(ty2) Memory.storeInt(addr.toInt, offset, value.toInt) - eval(rest, kont, mkont, trail)(newCtx2) - case Nop => eval(rest, kont, mkont, trail) + eval(rest, kont, mkont, trail)(ct2) + case Nop => eval(rest, kont, mkont, trail)(ct) case Load(LoadOp(align, offset, ty, None, None)) => - val (addr, newCtx1) = Stack.pop() - val value = Memory.loadInt(addr.toInt, offset) - val newCtx2 = Stack.push(value)(newCtx1) - eval(rest, kont, mkont, trail)(newCtx2) + val (ty1, ct1) = ct.pop() + val addr = Stack.popC(ty1) + val num = Memory.loadIntC(addr.toInt, offset) + Stack.pushC(num) + val ct2 = ct1.push(ty) + eval(rest, kont, mkont, trail)(ct2) case MemorySize => ??? case MemoryGrow => - val (delta, newCtx1) = Stack.pop() + val (ty, ct1) = ct.pop() + val delta = Stack.popC(ty) val ret = Memory.grow(delta.toInt) val retNum = Values.I32V(ret) - val retSym = "Concrete".reflectCtrlWith[SymVal](retNum) - val newCtx2 = Stack.push(I32(retNum, retSym))(newCtx1) - eval(rest, kont, mkont, trail)(newCtx2) + // For now, we assume that the result of memory.grow only depends on the execution path, + // we can relax this by turning it return to a symbol value and mimic the memory.grow's result as input. + Stack.pushC(I32C(retNum)) + val ct2 = ct1.push(NumType(I32Type)) + eval(rest, kont, mkont, trail)(ct2) case MemoryFill => ??? case Unreachable => unreachable() case Test(op) => - val (v, newCtx1) = Stack.pop() - val newCtx2 = Stack.push(evalTestOp(op, v))(newCtx1) - eval(rest, kont, mkont, trail)(newCtx2) + val (ty, ct1) = ct.pop() + val v = Stack.popC(ty) + Stack.pushC(evalTestOpC(op, v)) + val ct2 = ct1.push(v.tipe) + eval(rest, kont, mkont, trail)(ct2) case Unary(op) => - val (v, newCtx1) = Stack.pop() - val newCtx2 = Stack.push(evalUnaryOp(op, v))(newCtx1) - eval(rest, kont, mkont, trail)(newCtx2) + val (ty, ct1) = ct.pop() + val v = Stack.popC(ty) + val res = evalUnaryOpC(op, v) + Stack.pushC(res) + val ct2 = ct1.push(res.tipe) + eval(rest, kont, mkont, trail)(ct2) case Binary(op) => - val (v2, newCtx1) = Stack.pop() - val (v1, newCtx2) = Stack.pop()(newCtx1) - val newCtx3 = Stack.push(evalBinOp(op, v1, v2))(newCtx2) - eval(rest, kont, mkont, trail)(newCtx3) + val (ty2, ct1) = ct.pop() + val v2 = Stack.popC(ty2) + val (ty1, ct2) = ct1.pop() + val v1 = Stack.popC(ty1) + val res = evalBinOpC(op, v1, v2) + Stack.pushC(res) + val ct3 = ct2.push(res.tipe) + eval(rest, kont, mkont, trail)(ct3) case Compare(op) => - val (v2, newCtx1) = Stack.pop() - val (v1, newCtx2) = Stack.pop()(newCtx1) - val newCtx3 = Stack.push(evalRelOp(op, v1, v2))(newCtx2) - eval(rest, kont, mkont, trail)(newCtx3) + val (ty2, ct1) = ct.pop() + val v2 = Stack.popC(ty2) + val (ty1, ct2) = ct1.pop() + val v1 = Stack.popC(ty1) + val res = evalRelOpC(op, v1, v2) + Stack.pushC(res) + val ct3 = ct2.push(res.tipe) + eval(rest, kont, mkont, trail)(ct3) case WasmBlock(ty, inner) => // no need to modify the stack when entering a block // the type system guarantees that we will never take more than the input size from the stack val funcTy = ty.funcType - val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val exitSize = ct.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size val dummy = makeDummy - def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the block, stackSize =", Stack.size) - val offset = restCtx.stackTypes.size - exitSize - val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) - eval(rest, kont, mk, trail)(newRestCtx) + val offset = ct.endCtx.stackTypes.size - exitSize + Stack.shiftC(offset, funcTy.out.size) + if (isSymStateInUse) { + Stack.shiftS(offset, funcTy.out.size) + } + val ct1 = ct.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(ct1) }) - eval(inner, restK _, mkont, restK _ :: trail) + // TODO: extract this into a function + val (oldCtx, history, ct1) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + eval(inner, restK _, mkont, restK _ :: trail)(ct1) case Loop(ty, inner) => val funcTy = ty.funcType - val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val exitSize = ct.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size val dummy = makeDummy - def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the loop, stackSize =", Stack.size) - val offset = restCtx.stackTypes.size - exitSize - val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) - eval(rest, kont, mk, trail)(newRestCtx) + val offset = ct.endCtx.stackTypes.size - exitSize + Stack.shiftC(offset, funcTy.out.size) + if (isSymStateInUse) { + Stack.shiftS(offset, funcTy.out.size) + } + val ct1 = ct.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(ct1) }) - val enterSize = ctx.stackTypes.size - def loop(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + val enterSize = ct.endCtx.stackTypes.size + def loop(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Entered the loop, stackSize =", Stack.size) - val offset = restCtx.stackTypes.size - enterSize - val newRestCtx = Stack.shift(offset, funcTy.inps.size)(restCtx) - eval(inner, restK _, mk, loop _ :: trail)(newRestCtx) + val offset = ct.endCtx.stackTypes.size - enterSize + Stack.shiftC(offset, funcTy.inps.size) + if (isSymStateInUse) { + Stack.shiftS(offset, funcTy.inps.size) + } + val ct1 = ct.shift(offset, funcTy.inps.size) + eval(inner, restK _, mk, loop _ :: trail)(ct1) }) - loop(ctx)(mkont) + val (oldCtx, history, ct1) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + loop(ct1)(mkont) case If(ty, thn, els) => val funcTy = ty.funcType - val (cond, newCtx) = Stack.pop() - val exitSize = newCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size - // TODO: can we avoid code duplication here? - val dummy = makeDummy - def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + val (condTy, ct1) = ct.pop() + val cond = Stack.popC(condTy) + val exitSize = ct1.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size + def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the if, stackSize =", Stack.size) - val offset = restCtx.stackTypes.size - exitSize - val newRestCtx = Stack.shift(offset, funcTy.out.size)(restCtx) - eval(rest, kont, mk, trail)(newRestCtx) + val offset = ct.endCtx.stackTypes.size - exitSize + Stack.shiftC(offset, funcTy.out.size) + if (isSymStateInUse) { + Stack.shiftS(offset, funcTy.out.size) + } + val ct1 = ct.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(ct1) }) - // TODO: put the cond.s to path condition - ExploreTree.fillWithIfElse(cond.s) + val (oldCtx, history, ct2) = ct1.clearHistory + if (isSymStateInUse) { + // when we are not reusing + evalSym(history)(oldCtx) + val snapshot = makeSnapshot() + val symCond = Stack.popS(condTy) + ExploreTree.fillWithIfElse(symCond.s, snapshot) + } if (cond.toInt != 0) { ExploreTree.moveCursor(true) - eval(thn, restK _, mkont, restK _ :: trail)(newCtx) + eval(thn, restK _, mkont, restK _ :: trail)(ct2) } else { ExploreTree.moveCursor(false) - eval(els, restK _, mkont, restK _ :: trail)(newCtx) + eval(els, restK _, mkont, restK _ :: trail)(ct2) } () case Br(label) => info(s"Jump to $label") - trail(label)(ctx)(mkont) + val (oldCtx, history, ct1) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + trail(label)(ct1)(mkont) case BrIf(label) => - val (cond, newCtx) = Stack.pop() + val (ty, ct1) = ct.pop() + val cond = Stack.popC(ty) + val (oldCtx, history, ct2) = ct1.clearHistory info(s"The br_if(${label})'s condition is ", cond.toInt) - // TODO: put the cond.s to path condition - ExploreTree.fillWithIfElse(cond.s) + if (isSymStateInUse) { + evalSym(history)(oldCtx) + val symCond = Stack.popS(ty) + val snapshot = makeSnapshot() + ExploreTree.fillWithIfElse(symCond.s, snapshot) + } if (cond.toInt != 0) { info(s"Jump to $label") ExploreTree.moveCursor(true) - trail(label)(newCtx)(mkont) + trail(label)(ct2)(mkont) } else { info(s"Continue") ExploreTree.moveCursor(false) - eval(rest, kont, mkont, trail)(newCtx) + eval(rest, kont, mkont, trail)(ct2) } () case BrTable(labels, default) => - val (label, newCtx) = Stack.pop() + val (ty, ct1) = ct.pop() + val label = Stack.popC(ty) + val (oldCtx, history, ct2) = ct1.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } def aux(choices: List[Int], idx: Int): Rep[Unit] = { - if (choices.isEmpty) trail(default)(newCtx)(mkont) + if (choices.isEmpty) trail(default)(ct2)(mkont) else { val cond = (label - toStagedNum(I32V(idx))).isZero() - ExploreTree.fillWithIfElse(cond.s) + if (isSymStateInUse) { + val labelSym = Stack.peekS(ty) + val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() + val snapshot = makeSnapshot() + ExploreTree.fillWithIfElse(condSym.s, snapshot) + } if (cond.toInt != 0) { ExploreTree.moveCursor(true) - trail(choices.head)(newCtx)(mkont) + trail(choices.head)(ct2)(mkont) } else { ExploreTree.moveCursor(false) @@ -288,12 +470,142 @@ trait StagedWasmEvaluator extends SAIOps { } } aux(labels, 0) - case Return => trail.last(ctx)(mkont) - case Call(f) => evalCall(rest, kont, mkont, trail, f, false) - case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) + if (isSymStateInUse) { + Stack.popS(ty) + } + () + case Return => + // return instruction is also stack-polymorphic + val (oldCtx, history, ct2) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + trail.last(ct2)(mkont) + case Call(f) => evalCall(rest, kont, mkont, trail, f, false)(ct) + case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true)(ct) + case _ => + val todo = "todo-op".reflectCtrlWith[Unit]() + eval(rest, kont, mkont, trail)(ct) + } + } + + def replayAndClearHistory(ct: ContextTransition): ContextTransition = { + val (oldCtx, history, ct1) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } + ct1 + } + + // call the symbolic interpreter to evaluate the history that just executed by + // concrete interpreter + def evalSym(history: List[Instr]) + (ctx: Context): Rep[Unit] = { + // val func = topFun((_: Rep[Unit]) => evalS(history.reverse)) + // func(()) + evalS(history.reverse)(ctx) + } + + def evalS(insts: List[Instr]) + (ctx: Context): Rep[Unit] = { + if (insts.isEmpty) return () + + // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") + // Predef.println(s"[DEBUG] Current context: $ctx") + val (inst, rest) = (insts.head, insts.tail) + inst match { + case Drop => + val (ty, newCtx) = ctx.pop() + Stack.popS(ty) + evalS(rest)(newCtx) + case WasmConst(num) => + Stack.pushS(toStagedSymbolicNum(num)) + val newCtx = ctx.push(num.tipe(module)) + evalS(rest)(newCtx) + case Symbolic(ty) => + val id = Stack.popS(ty) + val symVal = id.makeSymbolic(ty) + Stack.pushS(symVal) + val newCtx = ctx.pop()._2.push(ty) + evalS(rest)(newCtx) + case LocalGet(i) => + Stack.pushS(Frames.getS(i)(ctx)) + val newCtx = ctx.push(ctx.frameTypes(i)) + evalS(rest)(newCtx) + case LocalSet(i) => + val (ty, newCtx) = ctx.pop() + val sym = Stack.popS(ty) + Frames.setS(i, sym) + evalS(rest)(newCtx) + case LocalTee(i) => + val ty = ctx.pop()._1 + val sym = Stack.peekS(ty) + Frames.setS(i, sym) + evalS(rest)(ctx) + case GlobalGet(i) => + Stack.pushS(Globals.getS(i)) + val newCtx = ctx.push(module.globals(i).ty.ty) + evalS(rest)(newCtx) + case GlobalSet(i) => + val (ty, newCtx) = ctx.pop() + val sym = Stack.popS(ty) + module.globals(i).ty match { + case GlobalType(tipe, true) => { + Globals.setS(i, sym) + } + case _ => throw new Exception("Cannot set immutable global") + } + evalS(rest)(newCtx) + case Nop => evalS(rest)(ctx) + case Store(StoreOp(align, offset, ty, None)) => ??? + case Load(LoadOp(align, offset, ty, None, None)) => ??? + case MemorySize => ??? + case MemoryGrow => ??? + case MemoryFill => ??? + case Unreachable => unreachable() + case Test(op) => + val (ty, newCtx1) = ctx.pop() + val s = Stack.popS(ty) + Stack.pushS(evalTestOpS(op, s)) + val newCtx2 = newCtx1.push(s.tipe) + evalS(rest)(newCtx2) + case Unary(op) => + val (ty, newCtx1) = ctx.pop() + val s = Stack.popS(ty) + val res = evalUnaryOpS(op, s) + Stack.pushS(res) + val newCtx2 = newCtx1.push(res.tipe) + evalS(rest)(newCtx2) + case Binary(op) => + val (ty2, newCtx1) = ctx.pop() + val s2 = Stack.popS(ty2) + val (ty1, newCtx2) = newCtx1.pop() + val s1 = Stack.popS(ty1) + val res = evalBinOpS(op, s1, s2) + Stack.pushS(res) + val newCtx3 = newCtx2.push(res.tipe) + evalS(rest)(newCtx3) + case Compare(op) => + val (ty2, newCtx1) = ctx.pop() + val s2 = Stack.popS(ty2) + val (ty1, newCtx2) = newCtx1.pop() + val s1 = Stack.popS(ty1) + val res = evalRelOpS(op, s1, s2) + Stack.pushS(res) + val newCtx3 = newCtx2.push(res.tipe) + evalS(rest)(newCtx3) + case WasmBlock(ty, inner) => () + case Loop(ty, inner) => () + case If(ty, thn, els) => () + case Br(label) => () + case BrIf(label) => () + case BrTable(labels, default) => () + case Return => () + case Call(f) => () + case ReturnCall(f) => () case _ => val todo = "todo-op".reflectCtrlWith[Unit]() - eval(rest, kont, mkont, trail) + evalS(rest)(ctx) } } @@ -301,12 +613,16 @@ trait StagedWasmEvaluator extends SAIOps { def evalCall(rest: List[Instr], - kont: Context => Rep[Cont[Unit]], + kont: CleanCT => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], trail: Trail[Unit], funcIndex: Int, isTail: Boolean) - (implicit ctx: Context): Rep[Unit] = { + (implicit ct: ContextTransition): Rep[Unit] = { + val (oldCtx, history, ct1) = ct.clearHistory + if (isSymStateInUse) { + evalSym(history)(oldCtx) + } module.funcs(funcIndex) match { case FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) => val locals = bodyLocals ++ ty.inps @@ -316,63 +632,102 @@ trait StagedWasmEvaluator extends SAIOps { } else { val callee = topFun((mk: Rep[MCont[Unit]]) => { info(s"Entered the function at $funcIndex, stackSize =", Stack.size) - // we can do some check here to ensure the function returns correct size of stack - eval(body, (_: Context) => forwardKont, mk, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) + // the return instruction is also stack polymorphic + def retK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + val offset = ct.ctx.stackTypes.size - ty.out.size + Stack.shiftC(offset, ty.out.size) + Stack.shiftS(offset, ty.out.size) + mk(()) + }) + eval(body, retK _, mk, retK _::Nil)(CleanCT(Context(Nil, locals))) }) compileCache(funcIndex) = callee callee } // Predef.println(s"[DEBUG] locals size: ${locals.size}") - val (args, newCtx) = Stack.take(ty.inps.size) + val ct2 = ct1.take(ty.inps.size) + val exitSize = ty.out.size + ct2.endCtx.stackTypes.size if (isTail) { // when tail call, return to the caller's return continuation - Frames.popFrame(ctx.frameTypes.size) - Frames.pushFrame(locals) - Frames.putAll(args) + val argsC = Stack.takeC(ty.inps) + Frames.popFrameC(ct2.endCtx.frameTypes.size) + Frames.pushFrameC(locals) + Frames.putAllC(argsC) + if (isSymStateInUse) { + val argsS = Stack.takeS(ty.inps) + Frames.popFrameS(ct2.endCtx.frameTypes.size) + Frames.pushFrameS(locals) + Frames.putAllS(argsS) + } callee(mkont) } else { // We make a new trail by `restK`, since function creates a new block to escape // (more or less like `return`) val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) - Frames.popFrame(locals.size) - eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) + Frames.popFrameC(locals.size) + Frames.popFrameS(locals.size) + val newCtx = ct2.endCtx.copy(stackTypes = ty.out.reverse ++ ct2.endCtx.stackTypes) + eval(rest, kont, mk, trail)(CleanCT(newCtx)) }) val dummy = makeDummy val newMKont: Rep[MCont[Unit]] = funHere((_u: Rep[Unit]) => { restK(mkont) }, dummy) - Frames.pushFrame(locals) - Frames.putAll(args) + val argsC = Stack.takeC(ty.inps) + Frames.pushFrameC(locals) + Frames.putAllC(argsC) + if (isSymStateInUse) { + val argsS = Stack.takeS(ty.inps) + Frames.pushFrameS(locals) + Frames.putAllS(argsS) + } callee(newMKont) } case Import("console", "log", _) | Import("spectest", "print_i32", _) => //println(s"[DEBUG] current stack: $stack") - val (v, newCtx) = Stack.pop() + val (ty, ct2) = ct1.pop() + val v = Stack.popC(ty) + Stack.popS(ty) println(v.toInt) - eval(rest, kont, mkont, trail)(newCtx) + eval(rest, kont, mkont, trail)(ct2) case Import("console", "assert", _) => - val (v, newCtx) = Stack.pop() + val (ty, ct2) = ct1.pop() + val v = Stack.popC(ty) + // TODO: We should also add s into exploration tree + val s = Stack.popS(ty) runtimeAssert(v.toInt != 0) - eval(rest, kont, mkont, trail)(newCtx) + eval(rest, kont, mkont, trail)(ct2) case Import(_, _, _) => throw new Exception(s"Unknown import at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } } - def evalTestOp(op: TestOp, value: StagedNum): StagedNum = op match { + def evalTestOpC(op: TestOp, value: StagedConcreteNum): StagedConcreteNum = op match { case Eqz(_) => value.isZero } - def evalUnaryOp(op: UnaryOp, value: StagedNum): StagedNum = op match { + def evalTestOpS(op: TestOp, value: StagedSymbolicNum): StagedSymbolicNum = op match { + case Eqz(_) => value.isZero + } + + def evalUnaryOpC(op: UnaryOp, value: StagedConcreteNum): StagedConcreteNum = op match { case Clz(_) => value.clz() case Ctz(_) => value.ctz() case Popcnt(_) => value.popcnt() case _ => ??? } - def evalBinOp(op: BinOp, v1: StagedNum, v2: StagedNum): StagedNum = op match { + def evalUnaryOpS(op: UnaryOp, value: StagedSymbolicNum): StagedSymbolicNum = op match { + case Clz(_) => value.clz() + case Ctz(_) => value.ctz() + case Popcnt(_) => value.popcnt() + case _ => ??? + } + + def evalBinOpC(op: BinOp, v1: StagedConcreteNum, v2: StagedConcreteNum): StagedConcreteNum = op match { case Add(_) => v1 + v2 case Mul(_) => v1 * v2 case Sub(_) => v1 - v2 @@ -386,7 +741,35 @@ trait StagedWasmEvaluator extends SAIOps { throw new Exception(s"Unknown binary operation $op") } - def evalRelOp(op: RelOp, v1: StagedNum, v2: StagedNum): StagedNum = op match { + def evalBinOpS(op: BinOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum): StagedSymbolicNum = op match { + case Add(_) => v1 + v2 + case Mul(_) => v1 * v2 + case Sub(_) => v1 - v2 + case Shl(_) => v1 << v2 + // case ShrS(_) => v1 >> v2 // TODO: signed shift right + case ShrU(_) => v1 >> v2 + case And(_) => v1 & v2 + case DivS(_) => v1 / v2 + case DivU(_) => v1 / v2 + case _ => + throw new Exception(s"Unknown binary operation $op") + } + + def evalRelOpC(op: RelOp, v1: StagedConcreteNum, v2: StagedConcreteNum): StagedConcreteNum = op match { + case Eq(_) => v1 numEq v2 + case Ne(_) => v1 numNe v2 + case LtS(_) => v1 < v2 + case LtU(_) => v1 ltu v2 + case GtS(_) => v1 > v2 + case GtU(_) => v1 gtu v2 + case LeS(_) => v1 <= v2 + case LeU(_) => v1 leu v2 + case GeS(_) => v1 >= v2 + case GeU(_) => v1 geu v2 + case _ => ??? + } + + def evalRelOpS(op: RelOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum): StagedSymbolicNum = op match { case Eq(_) => v1 numEq v2 case Ne(_) => v1 numNe v2 case LtS(_) => v1 < v2 @@ -426,12 +809,14 @@ trait StagedWasmEvaluator extends SAIOps { } val (instrs, locals) = (funBody.body, funBody.locals) resetStacks() - Frames.pushFrame(locals) - eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) - Frames.popFrame(locals.size) + Frames.pushFrameC(locals) + Frames.pushFrameS(locals) + eval(instrs, _ => forwardKont, mkont, ((_: CleanCT) => forwardKont)::Nil)(CleanCT(Context(Nil, locals))) + Frames.popFrameC(locals.size) + Frames.popFrameS(locals.size) } - def evalTop(main: Option[String], printRes: Boolean, dumpTree: Option[String]): Rep[Unit] = { + def evalTop(main: Option[String], printRes: Boolean): Rep[Unit] = { val haltK: Rep[Unit] => Rep[Unit] = (_) => { info("Exiting the program...") if (printRes) { @@ -450,66 +835,78 @@ trait StagedWasmEvaluator extends SAIOps { // stack operations object Stack { - def shift(offset: Int, size: Int)(ctx: Context): Context = { + def shiftC(offset: Int, size: Int) = { if (offset > 0) { "stack-shift".reflectCtrlWith[Unit](offset, size) } - ctx.shift(offset, size) + } + + def shiftS(offset: Int, size: Int) = { + if (offset > 0) { + "sym-stack-shift".reflectCtrlWith[Unit](offset, size) + } } def initialize(): Rep[Unit] = { "stack-init".reflectCtrlWith[Unit]() } - def pop()(implicit ctx: Context): (StagedNum, Context) = { - val (ty, newContext) = ctx.pop() - val num = ty match { - case NumType(I32Type) => I32("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(I64Type) => I64("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F32("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F64("stack-pop".reflectCtrlWith[Num](), "sym-stack-pop".reflectCtrlWith[SymVal]()) - } - (num, newContext) + def popC(ty: ValueType): StagedConcreteNum = ty match { + case NumType(I32Type) => I32C("stack-pop".reflectCtrlWith[Num]()) + case NumType(I64Type) => I64C("stack-pop".reflectCtrlWith[Num]()) + case NumType(F32Type) => F32C("stack-pop".reflectCtrlWith[Num]()) + case NumType(F32Type) => F64C("stack-pop".reflectCtrlWith[Num]()) } - def peek(implicit ctx: Context): (StagedNum, Context) = { - val ty = ctx.stackTypes.head - val num = ty match { - case NumType(I32Type) => I32("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(I64Type) => I64("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F32("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F64("stack-peek".reflectCtrlWith[Num](), "sym-stack-peek".reflectCtrlWith[SymVal]()) - } - (num, ctx) + def popS(ty: ValueType): StagedSymbolicNum = ty match { + case NumType(I32Type) => I32S("sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(I64Type) => I64S("sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F32S("sym-stack-pop".reflectCtrlWith[SymVal]()) + case NumType(F64Type) => F64S("sym-stack-pop".reflectCtrlWith[SymVal]()) } - def push(num: StagedNum)(implicit ctx: Context): Context = { - num match { - case I32(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) - case I64(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) - case F32(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) - case F64(v, s) => "stack-push".reflectCtrlWith[Unit](v); "sym-stack-push".reflectCtrlWith[Unit](s) - } - ctx.push(num.tipe) + def peekC(ty: ValueType): StagedConcreteNum = ty match { + case NumType(I32Type) => I32C("stack-peek".reflectCtrlWith[Num]()) + case NumType(I64Type) => I64C("stack-peek".reflectCtrlWith[Num]()) + case NumType(F32Type) => F32C("stack-peek".reflectCtrlWith[Num]()) + case NumType(F32Type) => F64C("stack-peek".reflectCtrlWith[Num]()) } - def take(n: Int)(implicit ctx: Context): (List[StagedNum], Context) = n match { - case 0 => (Nil, ctx) - case n => - val (v, newCtx1) = pop() - val (rest, newCtx2) = take(n - 1) - (v::rest, newCtx2) + def peekS(ty: ValueType): StagedSymbolicNum = ty match { + case NumType(I32Type) => I32S("sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(I64Type) => I64S("sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(F32Type) => F32S("sym-stack-peek".reflectCtrlWith[SymVal]()) + case NumType(F64Type) => F64S("sym-stack-peek".reflectCtrlWith[SymVal]()) } - def drop(n: Int)(implicit ctx: Context): Context = { - take(n)._2 + def pushC(num: StagedConcreteNum) = num match { + case I32C(v) => "stack-push".reflectCtrlWith[Unit](v) + case I64C(v) => "stack-push".reflectCtrlWith[Unit](v) + case F32C(v) => "stack-push".reflectCtrlWith[Unit](v) + case F64C(v) => "stack-push".reflectCtrlWith[Unit](v) } - def shift(offset: Rep[Int], size: Rep[Int]): Rep[Unit] = { - if (offset > 0) { - "stack-shift".reflectCtrlWith[Unit](offset, size) - "sym-stack-shift".reflectCtrlWith[Unit](offset, size) - } + def pushS(num: StagedSymbolicNum) = num match { + case I32S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) + case I64S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) + case F32S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) + case F64S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) + } + + def takeC(types: List[ValueType]): List[StagedConcreteNum] = types match { + case Nil => Nil + case t :: ts => + val v = popC(t) + val rest = takeC(ts) + v :: rest + } + + def takeS(types: List[ValueType]): List[StagedSymbolicNum] = types match { + case Nil => Nil + case t :: ts => + val v = popS(t) + val rest = takeS(ts) + v :: rest } def print(): Rep[Unit] = { @@ -522,41 +919,72 @@ trait StagedWasmEvaluator extends SAIOps { } object Frames { - def get(i: Int)(implicit ctx: Context): StagedNum = { + def getC(i: Int)(implicit ctx: Context): StagedConcreteNum = { // val offset = ctx.frameTypes.take(i).map(_.size).sum ctx.frameTypes(i) match { - case NumType(I32Type) => I32("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(I64Type) => I64("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(F32Type) => F32("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(F64Type) => F64("frame-get".reflectCtrlWith[Num](i), "sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(I32Type) => I32C("frame-get".reflectCtrlWith[Num](i)) + case NumType(I64Type) => I64C("frame-get".reflectCtrlWith[Num](i)) + case NumType(F32Type) => F32C("frame-get".reflectCtrlWith[Num](i)) + case NumType(F64Type) => F64C("frame-get".reflectCtrlWith[Num](i)) } } - def set(i: Int, v: StagedNum)(implicit ctx: Context): Rep[Unit] = { - // val offset = ctx.frameTypes.take(i).map(_.size).sum + def getS(i: Int)(implicit ctx: Context): StagedSymbolicNum = { + ctx.frameTypes(i) match { + case NumType(I32Type) => I32S("sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(I64Type) => I64S("sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(F32Type) => F32S("sym-frame-get".reflectCtrlWith[SymVal](i)) + case NumType(F64Type) => F64S("sym-frame-get".reflectCtrlWith[SymVal](i)) + } + } + + def setC(i: Int, v: StagedConcreteNum): Rep[Unit] = { v match { - case I32(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) - case I64(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) - case F32(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) - case F64(v, s) => "frame-set".reflectCtrlWith[Unit](i, v); "sym-frame-set".reflectCtrlWith[Unit](i, s) + case I32C(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case I64C(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case F32C(v) => "frame-set".reflectCtrlWith[Unit](i, v) + case F64C(v) => "frame-set".reflectCtrlWith[Unit](i, v) + } + } + + def setS(i: Int, s: StagedSymbolicNum): Rep[Unit] = { + s match { + case I32S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) + case I64S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) + case F32S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) + case F64S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) } } - def pushFrame(locals: List[ValueType]): Rep[Unit] = { + def pushFrameC(locals: List[ValueType]): Rep[Unit] = { // Predef.println(s"[DEBUG] push frame: $locals") val size = locals.size "frame-push".reflectCtrlWith[Unit](size) + } + + def pushFrameS(locals: List[ValueType]): Rep[Unit] = { + // Predef.println(s"[DEBUG] push frame: $locals") + val size = locals.size "sym-frame-push".reflectCtrlWith[Unit](size) } - def popFrame(size: Int): Rep[Unit] = { + def popFrameC(size: Int): Rep[Unit] = { "frame-pop".reflectCtrlWith[Unit](size) + } + + def popFrameS(size: Int): Rep[Unit] = { "sym-frame-pop".reflectCtrlWith[Unit](size) } - def putAll(args: List[StagedNum])(implicit ctx: Context): Rep[Unit] = { + def putAllC(args: List[StagedConcreteNum]): Rep[Unit] = { for ((arg, i) <- args.view.reverse.zipWithIndex) { - Frames.set(i, arg) + Frames.setC(i, arg) + } + } + + def putAllS(args: List[StagedSymbolicNum]): Rep[Unit] = { + for ((arg, i) <- args.view.reverse.zipWithIndex) { + Frames.setS(i, arg) } } } @@ -567,8 +995,12 @@ trait StagedWasmEvaluator extends SAIOps { // todo: store symbolic value to memory via extract/concat operation } - def loadInt(base: Rep[Int], offset: Int): StagedNum = { - I32("I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset)), "sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) + def loadIntC(base: Rep[Int], offset: Int): StagedConcreteNum = { + I32C("I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset))) + } + + def loadIntS(base: Rep[Int], offset: Int): StagedSymbolicNum = { + I32S("sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) } // Returns the previous memory size on success, or -1 if the memory cannot be grown. @@ -603,29 +1035,47 @@ trait StagedWasmEvaluator extends SAIOps { // global read/write object Globals { - def apply(i: Int): StagedNum = { + def getC(i: Int): StagedConcreteNum = { module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => I32("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(I64Type), _) => I64("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(F32Type), _) => F32("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(F64Type), _) => F64("global-get".reflectCtrlWith[Num](i), "sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(I32Type), _) => I32C("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(I64Type), _) => I64C("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(F32Type), _) => F32C("global-get".reflectCtrlWith[Num](i)) + case GlobalType(NumType(F64Type), _) => F64C("global-get".reflectCtrlWith[Num](i)) } } - def update(i: Int, v: StagedNum): Rep[Unit] = { + def getS(i: Int): StagedSymbolicNum = { module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) - case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) - case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) - case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i);"sym-global-set".reflectCtrlWith[Unit](i, v.s) + case GlobalType(NumType(I32Type), _) => I32S("sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(I64Type), _) => I64S("sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(F32Type), _) => F32S("sym-global-get".reflectCtrlWith[SymVal](i)) + case GlobalType(NumType(F64Type), _) => F64S("sym-global-get".reflectCtrlWith[SymVal](i)) + } + } + + def setC(i: Int, v: StagedConcreteNum): Rep[Unit] = { + module.globals(i).ty match { + case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) + case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) + case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) + case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) + } + } + + def setS(i: Int, s: StagedSymbolicNum): Rep[Unit] = { + module.globals(i).ty match { + case GlobalType(NumType(I32Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) + case GlobalType(NumType(I64Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) + case GlobalType(NumType(F32Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) + case GlobalType(NumType(F64Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) } } } // Exploration tree, object ExploreTree { - def fillWithIfElse(s: Rep[SymVal]): Rep[Unit] = { - "tree-fill-if-else".reflectCtrlWith[Unit](s) + def fillWithIfElse(sym: Rep[SymVal], snapshot: Rep[Snapshot]): Rep[Unit] = { + "tree-fill-if-else".reflectCtrlWith[Unit](sym, snapshot) } def fillWithFinished(): Rep[Unit] = { @@ -633,6 +1083,7 @@ trait StagedWasmEvaluator extends SAIOps { } def moveCursor(branch: Boolean): Rep[Unit] = { + // when moving cursor from to an unexplored node, we need to change the reuse state "tree-move-cursor".reflectCtrlWith[Unit](branch) } @@ -651,165 +1102,337 @@ trait StagedWasmEvaluator extends SAIOps { } } + object ReuseManager { + def isReusing: Rep[Boolean] = { + "reuse-is-reusing".reflectCtrlWith[Boolean]() + } + + def turnOnReuse(): Rep[Unit] = { + "reuse-turn-on".reflectCtrlWith[Unit]() + } + + def turnOffReuse(): Rep[Unit] = { + "reuse-turn-off".reflectCtrlWith[Unit]() + } + } + // runtime Num type - implicit class StagedNumOps(num: StagedNum) { + implicit class StagedConcreteNumOps(num: StagedConcreteNum) { + + def makeSymbolic(ty: ValueType): StagedSymbolicNum = num match { + case I32C(x) => I32S("make-symbolic-concrete".reflectCtrlWith[SymVal](num.toInt)) + } def toInt: Rep[Int] = "num-to-int".reflectCtrlWith[Int](num.i) - def isZero(): StagedNum = num match { - case I32(x_c, x_s) => I32(Values.I32V("is-zero".reflectCtrlWith[Int](num.toInt)), "sym-is-zero".reflectCtrlWith[SymVal](x_s)) + def isZero(): StagedConcreteNum = num match { + case I32C(x_c) => I32C(Values.I32V("is-zero".reflectCtrlWith[Int](num.toInt))) + } + + def clz(): StagedConcreteNum = num match { + case I32C(x) => I32C("clz".reflectCtrlWith[Num](x)) + case I64C(x) => I64C("clz".reflectCtrlWith[Num](x)) + } + + def ctz(): StagedConcreteNum = num match { + case I32C(x) => I32C("ctz".reflectCtrlWith[Num](x)) + case I64C(x) => I64C("ctz".reflectCtrlWith[Num](x)) + } + + def popcnt(): StagedConcreteNum = num match { + case I32C(x) => I32C("popcnt".reflectCtrlWith[Num](x)) + case I64C(x) => I64C("popcnt".reflectCtrlWith[Num](x)) + } + + def +(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-add".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-add".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-add".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-add".reflectCtrlWith[Num](x, y)) + } + } + + def -(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-sub".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-sub".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-sub".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-sub".reflectCtrlWith[Num](x, y)) + } + } + + def *(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-mul".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-mul".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-mul".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-mul".reflectCtrlWith[Num](x, y)) + } + } + + def /(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-div".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-div".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-div".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-div".reflectCtrlWith[Num](x, y)) + } + } + + def <<(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-shl".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-shl".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-shl".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-shl".reflectCtrlWith[Num](x, y)) + } + } + + def >>(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-shr".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-shr".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-shr".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-shr".reflectCtrlWith[Num](x, y)) + } + } + + def &(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("binary-and".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I64C("binary-and".reflectCtrlWith[Num](x, y)) + case (F32C(x), F32C(y)) => F32C("binary-and".reflectCtrlWith[Num](x, y)) + case (F64C(x), F64C(y)) => F64C("binary-and".reflectCtrlWith[Num](x, y)) + } + } + + def numEq(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-eq".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-eq".reflectCtrlWith[Num](x, y)) + } + } + + def numNe(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-ne".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-ne".reflectCtrlWith[Num](x, y)) + } + } + + def <(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-lt".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-lt".reflectCtrlWith[Num](x, y)) + } } - def clz(): StagedNum = num match { - case I32(x_c, x_s) => I32("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) - case I64(x_c, x_s) => I64("clz".reflectCtrlWith[Num](x_c), "sym-clz".reflectCtrlWith[SymVal](x_s)) + def ltu(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-ltu".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-ltu".reflectCtrlWith[Num](x, y)) + } } - def ctz(): StagedNum = num match { - case I32(x_c, x_s) => I32("ctz".reflectCtrlWith[Num](x_c), "sym-ctz".reflectCtrlWith[SymVal](x_s)) - case I64(x_c, x_s) => I64("ctz".reflectCtrlWith[Num](x_c), "sym-ctz".reflectCtrlWith[SymVal](x_s)) + def >(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-gt".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-gt".reflectCtrlWith[Num](x, y)) + } } - def popcnt(): StagedNum = num match { - case I32(x_c, x_s) => I32("popcnt".reflectCtrlWith[Num](x_c), "sym-popcnt".reflectCtrlWith[SymVal](x_s)) - case I64(x_c, x_s) => I64("popcnt".reflectCtrlWith[Num](x_c), "sym-popcnt".reflectCtrlWith[SymVal](x_s)) + def gtu(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-gtu".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-gtu".reflectCtrlWith[Num](x, y)) + } } - def makeSymbolic(): Rep[SymVal] = { - "make-symbolic".reflectCtrlWith[SymVal](num.s) + def <=(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-le".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-le".reflectCtrlWith[Num](x, y)) + } + } + + def leu(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-leu".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-leu".reflectCtrlWith[Num](x, y)) + } } - def +(rhs: StagedNum): StagedNum = { + def >=(rhs: StagedConcreteNum): StagedConcreteNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-add".reflectCtrlWith[Num](x_c, y_c), "sym-binary-add".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32C(x), I32C(y)) => I32C("relation-ge".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-ge".reflectCtrlWith[Num](x, y)) } } + def geu(rhs: StagedConcreteNum): StagedConcreteNum = { + (num, rhs) match { + case (I32C(x), I32C(y)) => I32C("relation-geu".reflectCtrlWith[Num](x, y)) + case (I64C(x), I64C(y)) => I32C("relation-geu".reflectCtrlWith[Num](x, y)) + } + } + } + + implicit class StagedSymbolicNumOps(num: StagedSymbolicNum) { + def makeSymbolic(ty: ValueType): StagedSymbolicNum = num match { + case I32S(x) => I32S("make-symbolic".reflectCtrlWith[SymVal](x)) + case _ => throw new RuntimeException("Symbol index must be an i32") + } + + def isZero(): StagedSymbolicNum = num match { + case I32S(x) => I32S("sym-is-zero".reflectCtrlWith[SymVal](x)) + } + + def clz(): StagedSymbolicNum = num match { + case I32S(x) => I32S("sym-clz".reflectCtrlWith[SymVal](x)) + case I64S(x) => I64S("sym-clz".reflectCtrlWith[SymVal](x)) + } + + def ctz(): StagedSymbolicNum = num match { + case I32S(x) => I32S("sym-ctz".reflectCtrlWith[SymVal](x)) + case I64S(x) => I64S("sym-ctz".reflectCtrlWith[SymVal](x)) + } + + def popcnt(): StagedSymbolicNum = num match { + case I32S(x) => I32S("sym-popcnt".reflectCtrlWith[SymVal](x)) + case I64S(x) => I64S("sym-popcnt".reflectCtrlWith[SymVal](x)) + } + + def +(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num, rhs) match { + case (I32S(x), I32S(y)) => I32S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) + } + } - def -(rhs: StagedNum): StagedNum = { + def -(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-sub".reflectCtrlWith[Num](x_c, y_c), "sym-binary-sub".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) } } - def *(rhs: StagedNum): StagedNum = { + def *(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-mul".reflectCtrlWith[Num](x_c, y_c), "sym-binary-mul".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) } } - def /(rhs: StagedNum): StagedNum = { + def /(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-div".reflectCtrlWith[Num](x_c, y_c), "sym-binary-div".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) } } - def <<(rhs: StagedNum): StagedNum = { + def <<(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-shl".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shl".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) } } - def >>(rhs: StagedNum): StagedNum = { + def >>(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-shr".reflectCtrlWith[Num](x_c, y_c), "sym-binary-shr".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) } } - def &(rhs: StagedNum): StagedNum = { + def &(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I64("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) - case (F32(x_c, x_s), F32(y_c, y_s)) => F32("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) - case (F64(x_c, x_s), F64(y_c, y_s)) => F64("binary-and".reflectCtrlWith[Num](x_c, y_c), "sym-binary-and".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I64S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) + case (F32S(x), F32S(y)) => F32S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) + case (F64S(x), F64S(y)) => F64S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) } } - def numEq(rhs: StagedNum): StagedNum = { + def numEq(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-eq".reflectCtrlWith[Num](x_c, y_c), "sym-relation-eq".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-eq".reflectCtrlWith[Num](x_c, y_c), "sym-relation-eq".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-eq".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-eq".reflectCtrlWith[SymVal](x, y)) } } - def numNe(rhs: StagedNum): StagedNum = { + def numNe(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ne".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ne".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ne".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ne".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-ne".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-ne".reflectCtrlWith[SymVal](x, y)) } } - def <(rhs: StagedNum): StagedNum = { + def <(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-lt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-lt".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-lt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-lt".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-lt".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-lt".reflectCtrlWith[SymVal](x, y)) } } - def ltu(rhs: StagedNum): StagedNum = { + def ltu(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ltu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ltu".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ltu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ltu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("relation-ltu".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("relation-ltu".reflectCtrlWith[SymVal](x, y)) } } - def >(rhs: StagedNum): StagedNum = { + def >(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-gt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gt".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-gt".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gt".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-gt".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-gt".reflectCtrlWith[SymVal](x, y)) } } - def gtu(rhs: StagedNum): StagedNum = { + def gtu(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-gtu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gtu".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-gtu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-gtu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-gtu".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-gtu".reflectCtrlWith[SymVal](x, y)) } } - def <=(rhs: StagedNum): StagedNum = { + def <=(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-le".reflectCtrlWith[Num](x_c, y_c), "sym-relation-le".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-le".reflectCtrlWith[Num](x_c, y_c), "sym-relation-le".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-le".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-le".reflectCtrlWith[SymVal](x, y)) } } - def leu(rhs: StagedNum): StagedNum = { + def leu(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-leu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-leu".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-leu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-leu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-leu".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-leu".reflectCtrlWith[SymVal](x, y)) } } - def >=(rhs: StagedNum): StagedNum = { + def >=(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-ge".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ge".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-ge".reflectCtrlWith[Num](x_c, y_c), "sym-relation-ge".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-ge".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-ge".reflectCtrlWith[SymVal](x, y)) } } - def geu(rhs: StagedNum): StagedNum = { + def geu(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num, rhs) match { - case (I32(x_c, x_s), I32(y_c, y_s)) => I32("relation-geu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-geu".reflectCtrlWith[SymVal](x_s, y_s)) - case (I64(x_c, x_s), I64(y_c, y_s)) => I32("relation-geu".reflectCtrlWith[Num](x_c, y_c), "sym-relation-geu".reflectCtrlWith[SymVal](x_s, y_s)) + case (I32S(x), I32S(y)) => I32S("sym-relation-geu".reflectCtrlWith[SymVal](x, y)) + case (I64S(x), I64S(y)) => I32S("sym-relation-geu".reflectCtrlWith[SymVal](x, y)) } } } @@ -848,7 +1471,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { else if (m.toString.endsWith("I32V")) "I32V" else if (m.toString.endsWith("I64V")) "I64V" else if (m.toString.endsWith("SymVal")) "SymVal" - + else if (m.toString.endsWith("Snapshot")) "Snapshot_t" else super.remap(m) } @@ -902,10 +1525,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.push("); shallow(value); emit(")") case Node(_, "stack-shift", List(offset, size), _) => emit("Stack.shift("); shallow(offset); emit(", "); shallow(size); emit(")") + case Node(_, "sym-stack-shift", List(offset, size), _) => + emit("SymStack.shift("); shallow(offset); emit(", "); shallow(size); emit(")") case Node(_, "stack-pop", _, _) => emit("Stack.pop()") case Node(_, "sym-stack-pop", _, _) => emit("SymStack.pop()") + case Node(_, "snapshot-make", _, _) => + emit("Snapshot_t()") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(")") case Node(_, "sym-frame-pop", List(i), _) => @@ -935,7 +1562,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "binary-add", List(lhs, rhs), _) => shallow(lhs); emit(" + "); shallow(rhs) case Node(_, "binary-sub", List(lhs, rhs), _) => - shallow(lhs); emit(" - "); shallow(rhs) + // todo: avoid using c++ operator, use explicit method call so operator's precedence issues won't exist + emit("("); shallow(lhs); emit(" - "); shallow(rhs); emit(")") case Node(_, "binary-mul", List(lhs, rhs), _) => shallow(lhs); emit(" * "); shallow(rhs) case Node(_, "binary-div", List(lhs, rhs), _) => @@ -990,12 +1618,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(num); emit(".toInt()") case Node(_, "make-symbolic", List(num), _) => shallow(num); emit(".makeSymbolic()") + case Node(_, "make-symbolic-concrete", List(num), _) => + emit("make_symbolic("); shallow(num); emit(")") case Node(_, "sym-env-read", List(sym), _) => emit("SymEnv.read("); shallow(sym); emit(")") case Node(_, "assert-true", List(cond), _) => emit("GENSYM_ASSERT("); shallow(cond); emit(")") - case Node(_, "tree-fill-if-else", List(s), _) => - emit("ExploreTree.fillIfElseNode("); shallow(s); emit(")") + case Node(_, "tree-fill-if-else", List(sym, snapshot), _) => + emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(", "); shallow(snapshot); emit(")") case Node(_, "tree-fill-finished", List(), _) => emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b), _) => @@ -1006,6 +1636,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.dump_graphviz("); shallow(f); emit(")") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") + case Node(_, "reuse-is-reusing", List(), _) => + emit("Reuse.is_reusing()") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => @@ -1063,12 +1695,12 @@ trait WasmToCppCompilerDriver[A, B] extends CppSAIDriver[A, B] with StagedWasmEv object WasmToCppCompiler { case class GeneratedCpp(source: String, headerFolders: List[String]) - def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean, dumpTree: Option[String]): GeneratedCpp = { + def compile(moduleInst: ModuleInstance, main: Option[String], printRes: Boolean): GeneratedCpp = { println(s"Now compiling wasm module with entry function $main") val driver = new WasmToCppCompilerDriver[Unit, Unit] { def module: ModuleInstance = moduleInst def snippet(x: Rep[Unit]): Rep[Unit] = { - evalTop(main, printRes, dumpTree) + evalTop(main, printRes) } } GeneratedCpp(driver.code, driver.codegen.includePaths.toList) @@ -1079,8 +1711,8 @@ object WasmToCppCompiler { outputCpp: String, outputExe: String, printRes: Boolean, - dumpTree: Option[String]): Unit = { - val generated = compile(moduleInst, main, printRes, dumpTree) + macros: String*): Unit = { + val generated = compile(moduleInst, main, printRes) val code = generated.source val writer = new java.io.PrintWriter(new java.io.File(outputCpp)) @@ -1091,7 +1723,9 @@ object WasmToCppCompiler { } import sys.process._ - val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g -l z3 " + generated.headerFolders.map(f => s"-I$f").mkString(" ") + val includeFlags = generated.headerFolders.map(f => s"-I$f").mkString(" ") + val macroFlags = macros.map(m => s"-D$m").mkString(" ") + val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g -l z3 " + includeFlags + " " + macroFlags if (command.! != 0) { throw new RuntimeException(s"Compilation failed for $outputCpp") } diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index a65d0edad..48c246342 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -9,12 +9,24 @@ import gensym.wasm.parser._ import gensym.wasm.stagedconcolicminiwasm._ class TestStagedConcolicEval extends FunSuite { - def testFileToCpp(filename: String, main: Option[String] = None, expect: Option[List[Float]]=None) = { + def testFileConcolicCpp(filename: String, main: Option[String] = None) = { val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" val exe = s"$cppFile.exe" val exploreTreeFile = s"$filename.tree.dot" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, Some(exploreTreeFile)) + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true) + + import sys.process._ + val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! + println(result) + } + + // only test concrete execution and its result + def testFileConcreteCpp(filename: String, main: Option[String] = None, expect: Option[List[Float]] = None) = { + val moduleInst = ModuleInstance(Parser.parseFile(filename)) + val cppFile = s"$filename.cpp" + val exe = s"$cppFile.exe" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, "NO_INFO", "RUN_ONCE") import sys.process._ val result = s"./$exe".!! @@ -30,13 +42,61 @@ class TestStagedConcolicEval extends FunSuite { }) } - test("ack-cpp") { testFileToCpp("./benchmarks/wasm/ack.wat", Some("real_main")) } + test("ack-cpp") { testFileConcolicCpp("./benchmarks/wasm/ack.wat", Some("real_main")) } test("bug-finding") { - testFileToCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) + testFileConcolicCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) } test("brtable-bug-finding") { - testFileToCpp("./benchmarks/wasm/staged/brtable_concolic.wat") + testFileConcolicCpp("./benchmarks/wasm/staged/brtable_concolic.wat") + } + + test("return-poly - concrete") { + testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) + } + test("ack-cpp - concrete") { testFileConcreteCpp("./benchmarks/wasm/ack.wat", Some("real_main"), expect=Some(List(7))) } + test("power - concrete") { testFileConcreteCpp("./benchmarks/wasm/pow.wat", Some("real_main"), expect=Some(List(1024))) } + test("start - concrete") { testFileConcreteCpp("./benchmarks/wasm/start.wat") } + test("fact - concrete") { testFileConcreteCpp("./benchmarks/wasm/fact.wat", None, expect=Some(List(120))) } + // TODO: Waiting more symbolic operators' implementations + // test("loop - concrete") { testFileConcreteCpp("./benchmarks/wasm/loop.wat", None, expect=Some(List(10))) } + test("even-odd - concrete") { testFileConcreteCpp("./benchmarks/wasm/even_odd.wat", None, expect=Some(List(1))) } + // TODO: Waiting symbolic memory's implementations + // test("load - concrete") { testFileConcreteCpp("./benchmarks/wasm/load.wat", None, expect=Some(List(1))) } + // test("btree - concrete") { testFileConcreteCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat") } + test("fib - concrete") { testFileConcreteCpp("./benchmarks/wasm/fib.wat", None, expect=Some(List(144))) } + test("tribonacci - concrete") { testFileConcreteCpp("./benchmarks/wasm/tribonacci.wat", None, expect=Some(List(504))) } + + // test("return - concrete") { + // Since all of the thrown exceptions had been captured in concolic driver, this test is not valid anymore + // intercept[java.lang.RuntimeException] { + // testFileConcreteCpp("./benchmarks/wasm/return.wat", Some("$real_main")) + // } + // } + + test("return_call - concrete") { + testFileConcreteCpp("./benchmarks/wasm/sum.wat", Some("sum10"), expect=Some(List(55))) + } + + test("block input - concrete") { + testFileConcreteCpp("./benchmarks/wasm/block.wat", Some("real_main"), expect=Some(List(9))) + } + test("loop block input - concrete") { + testFileConcreteCpp("./benchmarks/wasm/block.wat", Some("test_loop_input"), expect=Some(List(55))) + } + test("if block input - concrete") { + testFileConcreteCpp("./benchmarks/wasm/block.wat", Some("test_if_input"), expect=Some(List(25))) } + test("block input - poly br - concrete") { + testFileConcreteCpp("./benchmarks/wasm/block.wat", Some("test_poly_br"), expect=Some(List(0))) + } + test("loop block - poly br - concrete") { + testFileConcreteCpp("./benchmarks/wasm/loop_poly.wat", None, expect=Some(List(2, 1))) + } + + test("brtable-cpp - concrete") { + testFileConcreteCpp("./benchmarks/wasm/staged/brtable.wat") + } + } From 731ff9e14a6060b5c972bba2418ebaa3836baa8f Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 27 Aug 2025 19:28:49 -0400 Subject: [PATCH 023/105] c++17 compatible --- headers/wasm/smt_solver.hpp | 2 +- headers/wasm/utils.hpp | 14 ++++++++++++++ src/main/scala/wasm/StagedConcolicMiniWasm.scala | 2 +- 3 files changed, 16 insertions(+), 2 deletions(-) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index bc8cc9f94..504422f70 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -42,7 +42,7 @@ class Solver { z3::func_decl var = model[i]; z3::expr value = model.get_const_interp(var); std::string name = var.name().str(); - if (name.starts_with("s_")) { + if (starts_with(name, "s_")) { int id = std::stoi(name.substr(2)); if (id >= result.size()) { result.resize(id + 1); diff --git a/headers/wasm/utils.hpp b/headers/wasm/utils.hpp index ba57a1df0..f814858d3 100644 --- a/headers/wasm/utils.hpp +++ b/headers/wasm/utils.hpp @@ -36,4 +36,18 @@ #endif +#if __cplusplus < 202002L +#include + +inline bool starts_with(const std::string& str, const std::string& prefix) { + return str.size() >= prefix.size() && + std::equal(prefix.begin(), prefix.end(), str.begin()); +} +#else +#include +inline bool starts_with(const std::string& str, const std::string& prefix) { + return str.starts_with(prefix); +} +#endif + #endif // UTILS_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 769a0b85e..cfb2803a6 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -1725,7 +1725,7 @@ object WasmToCppCompiler { import sys.process._ val includeFlags = generated.headerFolders.map(f => s"-I$f").mkString(" ") val macroFlags = macros.map(m => s"-D$m").mkString(" ") - val command = s"g++ -std=c++20 $outputCpp -o $outputExe -O3 -g -l z3 " + includeFlags + " " + macroFlags + val command = s"g++ -std=c++17 $outputCpp -o $outputExe -O3 -g -l z3 " + includeFlags + " " + macroFlags if (command.! != 0) { throw new RuntimeException(s"Compilation failed for $outputCpp") } From ffa5670dbc470ae84124f14bb7845ec7a7d3b1fa Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 28 Aug 2025 20:49:33 -0400 Subject: [PATCH 024/105] fix --- headers/wasm/symbolic_rt.hpp | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 94351f077..566b5db6e 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -325,7 +325,7 @@ struct IfElseNode : Node { IfElseNode(SymVal cond, NodeBox *parent, Snapshot_t snapshot) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)) {} + false_branch(std::make_unique(parent)), snapshot(snapshot) {} std::string to_string() override { std::string result = "IfElseNode {\n"; From b57929ad4fcda386a8e43a672d9dec44572867ff Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Fri, 29 Aug 2025 16:14:10 -0400 Subject: [PATCH 025/105] revert: don't split concrete/symbolic interpreter & don't support snapshot for now --- headers/wasm/symbolic_rt.hpp | 33 +- .../scala/wasm/StagedConcolicMiniWasm.scala | 511 +++++------------- 2 files changed, 156 insertions(+), 388 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 566b5db6e..6efa7cfe0 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -269,7 +269,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond, const Snapshot_t &snapshot); + std::monostate fillIfElseNode(SymVal cond); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -321,11 +321,10 @@ struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; - Snapshot_t snapshot; - IfElseNode(SymVal cond, NodeBox *parent, Snapshot_t snapshot) + IfElseNode(SymVal cond, NodeBox *parent) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)), snapshot(snapshot) {} + false_branch(std::make_unique(parent)) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -438,11 +437,10 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond, - const Snapshot_t &snapshot) { +inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (dynamic_cast(node.get())) { - node = std::make_unique(cond, this, snapshot); + node = std::make_unique(cond, this); } assert( dynamic_cast(node.get()) != nullptr && @@ -545,8 +543,8 @@ class ExploreTree_t { std::monostate fillFailedNode() { return cursor->fillFailedNode(); } - std::monostate fillIfElseNode(SymVal cond, const Snapshot_t &snapshot) { - return cursor->fillIfElseNode(cond, snapshot); + std::monostate fillIfElseNode(SymVal cond) { + return cursor->fillIfElseNode(cond); } std::monostate moveCursor(bool branch) { @@ -561,23 +559,6 @@ class ExploreTree_t { cursor = if_else_node->false_branch.get(); } - if (dynamic_cast(cursor->node.get())) { - // If we meet an unexplored node, resume the snapshot before and keep - // going - -#ifdef DEBUG - std::cout << "Resuming snapshot for unexplored node" << std::endl; -#endif - if (Reuse.is_reusing()) { - Reuse.turn_off_reusing(); - SymStack.reuse(if_else_node->snapshot); - } - } else if (dynamic_cast(cursor->node.get())) { - // if we are moving to a branch node, we must have reused the symbolic - // states - assert((!REUSE_MODE || Reuse.is_reusing()) && - "Moving to a branch node without reusing symbolic states"); - } return std::monostate(); } diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index cfb2803a6..7372ede92 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -141,50 +141,11 @@ trait StagedWasmEvaluator extends SAIOps { ) } } - - } - - case class ContextTransition(startCtx: Context, history: List[Instr], endCtx: Context) { - def log(instr: Instr): ContextTransition = { - this.copy(history = instr :: history) - } - - def clearHistory: (Context, List[Instr], CleanCT) = { - (startCtx, history, CleanCT(endCtx)) - } - - def push(ty: ValueType): ContextTransition = { - this.copy(endCtx = endCtx.push(ty)) - } - - def peek: ValueType = { - endCtx.peek - } - - def pop(): (ValueType, ContextTransition) = { - val (ty, newCtx) = endCtx.pop() - (ty, this.copy(endCtx = newCtx)) - } - - def take(n: Int): ContextTransition = { - this.copy(endCtx = endCtx.take(n)) - } - - def shift(offset: Int, size: Int): ContextTransition = { - this.copy(endCtx = endCtx.shift(offset, size)) - } - } - - case class CleanCT(ctx: Context) - - // we can treat every CleanCT as a ContextTransition - implicit def toContextCT(ct: CleanCT): ContextTransition = { - ContextTransition(ct.ctx, Nil, ct.ctx) } type MCont[A] = Unit => A type Cont[A] = (MCont[A]) => A - type Trail[A] = List[CleanCT => Rep[Cont[A]]] + type Trail[A] = List[Context => Rep[Cont[A]]] // a cache storing the compiled code for each function, to reduce re-compilation val compileCache = new HashMap[Int, Rep[(MCont[Unit]) => Unit]] @@ -209,259 +170,243 @@ trait StagedWasmEvaluator extends SAIOps { "snapshot-make".reflectCtrlWith[Snapshot]() } - def isSymStateInUse: Rep[Boolean] = !ReuseManager.isReusing - def eval(insts: List[Instr], - kont: CleanCT => Rep[Cont[Unit]], + kont: Context => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], trail: Trail[Unit]) - (oldCT: ContextTransition): Rep[Unit] = { - if (insts.isEmpty) { - val (oldCtx, history, ct) = oldCT.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - return kont(ct)(mkont) - } + (implicit ctx: Context): Rep[Unit] = { + if (insts.isEmpty) return kont(ctx)(mkont) // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") // Predef.println(s"[DEBUG] Current context: $ctx") + val (inst, rest) = (insts.head, insts.tail) - val ct = oldCT.log(inst) inst match { case Drop => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() Stack.popC(ty) - eval(rest, kont, mkont, trail)(ct1) + Stack.popS(ty) + eval(rest, kont, mkont, trail)(newCtx) case WasmConst(num) => Stack.pushC(toStagedNum(num)) - val ct1 = ct.push(num.tipe(module)) - eval(rest, kont, mkont, trail)(ct1) + Stack.pushS(toStagedSymbolicNum(num)) + val newCtx = ctx.push(num.tipe(module)) + eval(rest, kont, mkont, trail)(newCtx) case Symbolic(ty) => - val id = Stack.popC(ty) + Stack.popC(ty) + val id = Stack.popS(ty) val symVal = id.makeSymbolic(ty) val num = SymEnv.read(symVal.s) Stack.pushC(ty.concreteTag(num)) - val ct1 = ct.pop()._2.push(ty) - eval(rest, kont, mkont, trail)(ct1) + Stack.pushS(symVal) + val newCtx = ctx.pop()._2.push(ty) + eval(rest, kont, mkont, trail)(newCtx) case LocalGet(i) => - Stack.pushC(Frames.getC(i)(ct.endCtx)) - val ct1 = ct.push(ct.endCtx.frameTypes(i)) - eval(rest, kont, mkont, trail)(ct1) + Stack.pushC(Frames.getC(i)) + Stack.pushS(Frames.getS(i)) + val newCtx = ctx.push(ctx.frameTypes(i)) + eval(rest, kont, mkont, trail)(newCtx) case LocalSet(i) => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() val num = Stack.popC(ty) + val sym = Stack.popS(ty) Frames.setC(i, num) - eval(rest, kont, mkont, trail)(ct1) + Frames.setS(i, sym) + eval(rest, kont, mkont, trail)(newCtx) case LocalTee(i) => - val ty = ct.peek + val ty = ctx.pop()._1 val num = Stack.peekC(ty) + val sym = Stack.peekS(ty) Frames.setC(i, num) - eval(rest, kont, mkont, trail)(ct) + Frames.setS(i, sym) + eval(rest, kont, mkont, trail)(ctx) case GlobalGet(i) => Stack.pushC(Globals.getC(i)) - val ct1 = ct.push(module.globals(i).ty.ty) - eval(rest, kont, mkont, trail)(ct1) + Stack.pushS(Globals.getS(i)) + val newCtx = ctx.push(module.globals(i).ty.ty) + eval(rest, kont, mkont, trail)(newCtx) case GlobalSet(i) => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() val num = Stack.popC(ty) + val sym = Stack.popS(ty) module.globals(i).ty match { case GlobalType(tipe, true) => { Globals.setC(i, num) + Globals.setS(i, sym) } case _ => throw new Exception("Cannot set immutable global") } - eval(rest, kont, mkont, trail)(ct1) + eval(rest, kont, mkont, trail)(newCtx) case Store(StoreOp(align, offset, ty, None)) => - val (ty1, ct1) = ct.pop() + val (ty1, newCtx1) = ctx.pop() val value = Stack.popC(ty1) - val (ty2, ct2) = ct1.pop() + val symValue = Stack.popS(ty1) + val (ty2, newCtx2) = newCtx1.pop() val addr = Stack.popC(ty2) + val symAddr = Stack.popS(ty2) Memory.storeInt(addr.toInt, offset, value.toInt) - eval(rest, kont, mkont, trail)(ct2) - case Nop => eval(rest, kont, mkont, trail)(ct) + eval(rest, kont, mkont, trail)(newCtx2) + case Nop => eval(rest, kont, mkont, trail) case Load(LoadOp(align, offset, ty, None, None)) => - val (ty1, ct1) = ct.pop() + val (ty1, newCtx1) = ctx.pop() val addr = Stack.popC(ty1) + Stack.popS(ty1) val num = Memory.loadIntC(addr.toInt, offset) + val sym = Memory.loadIntS(addr.toInt, offset) Stack.pushC(num) - val ct2 = ct1.push(ty) - eval(rest, kont, mkont, trail)(ct2) + Stack.pushS(sym) + val newCtx2 = newCtx1.push(ty) + eval(rest, kont, mkont, trail)(newCtx2) case MemorySize => ??? case MemoryGrow => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() val delta = Stack.popC(ty) + Stack.popS(ty) val ret = Memory.grow(delta.toInt) val retNum = Values.I32V(ret) // For now, we assume that the result of memory.grow only depends on the execution path, // we can relax this by turning it return to a symbol value and mimic the memory.grow's result as input. + val retSym = "Concrete".reflectCtrlWith[SymVal](retNum) Stack.pushC(I32C(retNum)) - val ct2 = ct1.push(NumType(I32Type)) - eval(rest, kont, mkont, trail)(ct2) + Stack.pushS(I32S(retSym)) + val newCtx2 = ctx.push(NumType(I32Type)) + eval(rest, kont, mkont, trail)(newCtx2) case MemoryFill => ??? case Unreachable => unreachable() case Test(op) => - val (ty, ct1) = ct.pop() + val (ty, newCtx1) = ctx.pop() val v = Stack.popC(ty) + val s = Stack.popS(ty) Stack.pushC(evalTestOpC(op, v)) - val ct2 = ct1.push(v.tipe) - eval(rest, kont, mkont, trail)(ct2) + Stack.pushS(evalTestOpS(op, s)) + val newCtx2 = newCtx1.push(v.tipe) + eval(rest, kont, mkont, trail)(newCtx2) case Unary(op) => - val (ty, ct1) = ct.pop() + val (ty, newCtx1) = ctx.pop() val v = Stack.popC(ty) + val s = Stack.popS(ty) val res = evalUnaryOpC(op, v) Stack.pushC(res) - val ct2 = ct1.push(res.tipe) - eval(rest, kont, mkont, trail)(ct2) + Stack.pushS(evalUnaryOpS(op, s)) + val newCtx2 = newCtx1.push(res.tipe) + eval(rest, kont, mkont, trail)(newCtx2) case Binary(op) => - val (ty2, ct1) = ct.pop() + val (ty2, newCtx1) = ctx.pop() val v2 = Stack.popC(ty2) - val (ty1, ct2) = ct1.pop() + val s2 = Stack.popS(ty2) + val (ty1, newCtx2) = newCtx1.pop() val v1 = Stack.popC(ty1) + val s1 = Stack.popS(ty1) val res = evalBinOpC(op, v1, v2) Stack.pushC(res) - val ct3 = ct2.push(res.tipe) - eval(rest, kont, mkont, trail)(ct3) + Stack.pushS(evalBinOpS(op, s1, s2)) + val newCtx3 = newCtx2.push(res.tipe) + eval(rest, kont, mkont, trail)(newCtx3) case Compare(op) => - val (ty2, ct1) = ct.pop() + val (ty2, newCtx1) = ctx.pop() val v2 = Stack.popC(ty2) - val (ty1, ct2) = ct1.pop() + val s2 = Stack.popS(ty2) + val (ty1, newCtx2) = newCtx1.pop() val v1 = Stack.popC(ty1) + val s1 = Stack.popS(ty1) val res = evalRelOpC(op, v1, v2) Stack.pushC(res) - val ct3 = ct2.push(res.tipe) - eval(rest, kont, mkont, trail)(ct3) + Stack.pushS(evalRelOpS(op, s1, s2)) + val newCtx3 = newCtx2.push(res.tipe) + eval(rest, kont, mkont, trail)(newCtx3) case WasmBlock(ty, inner) => // no need to modify the stack when entering a block // the type system guarantees that we will never take more than the input size from the stack val funcTy = ty.funcType - val exitSize = ct.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size val dummy = makeDummy - def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the block, stackSize =", Stack.size) - val offset = ct.endCtx.stackTypes.size - exitSize + val offset = restCtx.stackTypes.size - exitSize Stack.shiftC(offset, funcTy.out.size) - if (isSymStateInUse) { - Stack.shiftS(offset, funcTy.out.size) - } - val ct1 = ct.shift(offset, funcTy.out.size) - eval(rest, kont, mk, trail)(ct1) + Stack.shiftS(offset, funcTy.out.size) + val newRestCtx = restCtx.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(newRestCtx) }) - // TODO: extract this into a function - val (oldCtx, history, ct1) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - eval(inner, restK _, mkont, restK _ :: trail)(ct1) + eval(inner, restK _, mkont, restK _ :: trail) case Loop(ty, inner) => val funcTy = ty.funcType - val exitSize = ct.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size + val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size val dummy = makeDummy - def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the loop, stackSize =", Stack.size) - val offset = ct.endCtx.stackTypes.size - exitSize + val offset = restCtx.stackTypes.size - exitSize Stack.shiftC(offset, funcTy.out.size) - if (isSymStateInUse) { - Stack.shiftS(offset, funcTy.out.size) - } - val ct1 = ct.shift(offset, funcTy.out.size) - eval(rest, kont, mk, trail)(ct1) + Stack.shiftS(offset, funcTy.out.size) + val newRestCtx = restCtx.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(newRestCtx) }) - val enterSize = ct.endCtx.stackTypes.size - def loop(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + val enterSize = ctx.stackTypes.size + def loop(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Entered the loop, stackSize =", Stack.size) - val offset = ct.endCtx.stackTypes.size - enterSize + val offset = restCtx.stackTypes.size - enterSize Stack.shiftC(offset, funcTy.inps.size) - if (isSymStateInUse) { - Stack.shiftS(offset, funcTy.inps.size) - } - val ct1 = ct.shift(offset, funcTy.inps.size) - eval(inner, restK _, mk, loop _ :: trail)(ct1) + Stack.shiftS(offset, funcTy.inps.size) + val newRestCtx = restCtx.shift(offset, funcTy.inps.size) + eval(inner, restK _, mk, loop _ :: trail)(newRestCtx) }) - val (oldCtx, history, ct1) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - loop(ct1)(mkont) + loop(ctx)(mkont) case If(ty, thn, els) => val funcTy = ty.funcType - val (condTy, ct1) = ct.pop() + val (condTy, newCtx) = ctx.pop() val cond = Stack.popC(condTy) - val exitSize = ct1.endCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size - def restK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + val symCond = Stack.popS(condTy) + val exitSize = newCtx.stackTypes.size - funcTy.inps.size + funcTy.out.size + def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the if, stackSize =", Stack.size) - val offset = ct.endCtx.stackTypes.size - exitSize + val offset = restCtx.stackTypes.size - exitSize Stack.shiftC(offset, funcTy.out.size) - if (isSymStateInUse) { - Stack.shiftS(offset, funcTy.out.size) - } - val ct1 = ct.shift(offset, funcTy.out.size) - eval(rest, kont, mk, trail)(ct1) + Stack.shiftS(offset, funcTy.out.size) + val newRestCtx = restCtx.shift(offset, funcTy.out.size) + eval(rest, kont, mk, trail)(newRestCtx) }) - val (oldCtx, history, ct2) = ct1.clearHistory - if (isSymStateInUse) { - // when we are not reusing - evalSym(history)(oldCtx) - val snapshot = makeSnapshot() - val symCond = Stack.popS(condTy) - ExploreTree.fillWithIfElse(symCond.s, snapshot) - } + // TODO: put the cond.s to path condition + ExploreTree.fillWithIfElse(symCond.s) if (cond.toInt != 0) { ExploreTree.moveCursor(true) - eval(thn, restK _, mkont, restK _ :: trail)(ct2) + eval(thn, restK _, mkont, restK _ :: trail)(newCtx) } else { ExploreTree.moveCursor(false) - eval(els, restK _, mkont, restK _ :: trail)(ct2) + eval(els, restK _, mkont, restK _ :: trail)(newCtx) } () case Br(label) => info(s"Jump to $label") - val (oldCtx, history, ct1) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - trail(label)(ct1)(mkont) + trail(label)(ctx)(mkont) case BrIf(label) => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() val cond = Stack.popC(ty) - val (oldCtx, history, ct2) = ct1.clearHistory + val symCond = Stack.popS(ty) info(s"The br_if(${label})'s condition is ", cond.toInt) - if (isSymStateInUse) { - evalSym(history)(oldCtx) - val symCond = Stack.popS(ty) - val snapshot = makeSnapshot() - ExploreTree.fillWithIfElse(symCond.s, snapshot) - } + ExploreTree.fillWithIfElse(symCond.s) if (cond.toInt != 0) { info(s"Jump to $label") ExploreTree.moveCursor(true) - trail(label)(ct2)(mkont) + trail(label)(newCtx)(mkont) } else { info(s"Continue") ExploreTree.moveCursor(false) - eval(rest, kont, mkont, trail)(ct2) + eval(rest, kont, mkont, trail)(newCtx) } () case BrTable(labels, default) => - val (ty, ct1) = ct.pop() + val (ty, newCtx) = ctx.pop() val label = Stack.popC(ty) - val (oldCtx, history, ct2) = ct1.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } + val labelSym = Stack.popS(ty) def aux(choices: List[Int], idx: Int): Rep[Unit] = { - if (choices.isEmpty) trail(default)(ct2)(mkont) + if (choices.isEmpty) trail(default)(newCtx)(mkont) else { val cond = (label - toStagedNum(I32V(idx))).isZero() - if (isSymStateInUse) { - val labelSym = Stack.peekS(ty) - val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() - val snapshot = makeSnapshot() - ExploreTree.fillWithIfElse(condSym.s, snapshot) - } + val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() + ExploreTree.fillWithIfElse(condSym.s) if (cond.toInt != 0) { ExploreTree.moveCursor(true) - trail(choices.head)(ct2)(mkont) + trail(choices.head)(newCtx)(mkont) } else { ExploreTree.moveCursor(false) @@ -470,142 +415,12 @@ trait StagedWasmEvaluator extends SAIOps { } } aux(labels, 0) - if (isSymStateInUse) { - Stack.popS(ty) - } - () - case Return => - // return instruction is also stack-polymorphic - val (oldCtx, history, ct2) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - trail.last(ct2)(mkont) - case Call(f) => evalCall(rest, kont, mkont, trail, f, false)(ct) - case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true)(ct) + case Return => trail.last(ctx)(mkont) + case Call(f) => evalCall(rest, kont, mkont, trail, f, false) + case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) case _ => val todo = "todo-op".reflectCtrlWith[Unit]() - eval(rest, kont, mkont, trail)(ct) - } - } - - def replayAndClearHistory(ct: ContextTransition): ContextTransition = { - val (oldCtx, history, ct1) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } - ct1 - } - - // call the symbolic interpreter to evaluate the history that just executed by - // concrete interpreter - def evalSym(history: List[Instr]) - (ctx: Context): Rep[Unit] = { - // val func = topFun((_: Rep[Unit]) => evalS(history.reverse)) - // func(()) - evalS(history.reverse)(ctx) - } - - def evalS(insts: List[Instr]) - (ctx: Context): Rep[Unit] = { - if (insts.isEmpty) return () - - // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") - // Predef.println(s"[DEBUG] Current context: $ctx") - val (inst, rest) = (insts.head, insts.tail) - inst match { - case Drop => - val (ty, newCtx) = ctx.pop() - Stack.popS(ty) - evalS(rest)(newCtx) - case WasmConst(num) => - Stack.pushS(toStagedSymbolicNum(num)) - val newCtx = ctx.push(num.tipe(module)) - evalS(rest)(newCtx) - case Symbolic(ty) => - val id = Stack.popS(ty) - val symVal = id.makeSymbolic(ty) - Stack.pushS(symVal) - val newCtx = ctx.pop()._2.push(ty) - evalS(rest)(newCtx) - case LocalGet(i) => - Stack.pushS(Frames.getS(i)(ctx)) - val newCtx = ctx.push(ctx.frameTypes(i)) - evalS(rest)(newCtx) - case LocalSet(i) => - val (ty, newCtx) = ctx.pop() - val sym = Stack.popS(ty) - Frames.setS(i, sym) - evalS(rest)(newCtx) - case LocalTee(i) => - val ty = ctx.pop()._1 - val sym = Stack.peekS(ty) - Frames.setS(i, sym) - evalS(rest)(ctx) - case GlobalGet(i) => - Stack.pushS(Globals.getS(i)) - val newCtx = ctx.push(module.globals(i).ty.ty) - evalS(rest)(newCtx) - case GlobalSet(i) => - val (ty, newCtx) = ctx.pop() - val sym = Stack.popS(ty) - module.globals(i).ty match { - case GlobalType(tipe, true) => { - Globals.setS(i, sym) - } - case _ => throw new Exception("Cannot set immutable global") - } - evalS(rest)(newCtx) - case Nop => evalS(rest)(ctx) - case Store(StoreOp(align, offset, ty, None)) => ??? - case Load(LoadOp(align, offset, ty, None, None)) => ??? - case MemorySize => ??? - case MemoryGrow => ??? - case MemoryFill => ??? - case Unreachable => unreachable() - case Test(op) => - val (ty, newCtx1) = ctx.pop() - val s = Stack.popS(ty) - Stack.pushS(evalTestOpS(op, s)) - val newCtx2 = newCtx1.push(s.tipe) - evalS(rest)(newCtx2) - case Unary(op) => - val (ty, newCtx1) = ctx.pop() - val s = Stack.popS(ty) - val res = evalUnaryOpS(op, s) - Stack.pushS(res) - val newCtx2 = newCtx1.push(res.tipe) - evalS(rest)(newCtx2) - case Binary(op) => - val (ty2, newCtx1) = ctx.pop() - val s2 = Stack.popS(ty2) - val (ty1, newCtx2) = newCtx1.pop() - val s1 = Stack.popS(ty1) - val res = evalBinOpS(op, s1, s2) - Stack.pushS(res) - val newCtx3 = newCtx2.push(res.tipe) - evalS(rest)(newCtx3) - case Compare(op) => - val (ty2, newCtx1) = ctx.pop() - val s2 = Stack.popS(ty2) - val (ty1, newCtx2) = newCtx1.pop() - val s1 = Stack.popS(ty1) - val res = evalRelOpS(op, s1, s2) - Stack.pushS(res) - val newCtx3 = newCtx2.push(res.tipe) - evalS(rest)(newCtx3) - case WasmBlock(ty, inner) => () - case Loop(ty, inner) => () - case If(ty, thn, els) => () - case Br(label) => () - case BrIf(label) => () - case BrTable(labels, default) => () - case Return => () - case Call(f) => () - case ReturnCall(f) => () - case _ => - val todo = "todo-op".reflectCtrlWith[Unit]() - evalS(rest)(ctx) + eval(rest, kont, mkont, trail) } } @@ -613,16 +428,12 @@ trait StagedWasmEvaluator extends SAIOps { def evalCall(rest: List[Instr], - kont: CleanCT => Rep[Cont[Unit]], + kont: Context => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], trail: Trail[Unit], funcIndex: Int, isTail: Boolean) - (implicit ct: ContextTransition): Rep[Unit] = { - val (oldCtx, history, ct1) = ct.clearHistory - if (isSymStateInUse) { - evalSym(history)(oldCtx) - } + (implicit ctx: Context): Rep[Unit] = { module.funcs(funcIndex) match { case FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) => val locals = bodyLocals ++ ty.inps @@ -633,33 +444,30 @@ trait StagedWasmEvaluator extends SAIOps { val callee = topFun((mk: Rep[MCont[Unit]]) => { info(s"Entered the function at $funcIndex, stackSize =", Stack.size) // the return instruction is also stack polymorphic - def retK(ct: CleanCT): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + def retK(ctx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) - val offset = ct.ctx.stackTypes.size - ty.out.size + val offset = ctx.stackTypes.size - ty.out.size Stack.shiftC(offset, ty.out.size) Stack.shiftS(offset, ty.out.size) mk(()) }) - eval(body, retK _, mk, retK _::Nil)(CleanCT(Context(Nil, locals))) + eval(body, retK _, mk, retK _::Nil)(Context(Nil, locals)) }) compileCache(funcIndex) = callee callee } // Predef.println(s"[DEBUG] locals size: ${locals.size}") - val ct2 = ct1.take(ty.inps.size) - val exitSize = ty.out.size + ct2.endCtx.stackTypes.size + val newCtx = ctx.take(ty.inps.size) + val argsC = Stack.takeC(ty.inps) + val argsS = Stack.takeS(ty.inps) if (isTail) { // when tail call, return to the caller's return continuation - val argsC = Stack.takeC(ty.inps) - Frames.popFrameC(ct2.endCtx.frameTypes.size) + Frames.popFrameC(ctx.frameTypes.size) + Frames.popFrameS(ctx.frameTypes.size) Frames.pushFrameC(locals) + Frames.pushFrameS(locals) Frames.putAllC(argsC) - if (isSymStateInUse) { - val argsS = Stack.takeS(ty.inps) - Frames.popFrameS(ct2.endCtx.frameTypes.size) - Frames.pushFrameS(locals) - Frames.putAllS(argsS) - } + Frames.putAllS(argsS) callee(mkont) } else { // We make a new trail by `restK`, since function creates a new block to escape @@ -668,38 +476,33 @@ trait StagedWasmEvaluator extends SAIOps { info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) Frames.popFrameC(locals.size) Frames.popFrameS(locals.size) - val newCtx = ct2.endCtx.copy(stackTypes = ty.out.reverse ++ ct2.endCtx.stackTypes) - eval(rest, kont, mk, trail)(CleanCT(newCtx)) + eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) }) val dummy = makeDummy val newMKont: Rep[MCont[Unit]] = funHere((_u: Rep[Unit]) => { restK(mkont) }, dummy) - val argsC = Stack.takeC(ty.inps) Frames.pushFrameC(locals) + Frames.pushFrameS(locals) Frames.putAllC(argsC) - if (isSymStateInUse) { - val argsS = Stack.takeS(ty.inps) - Frames.pushFrameS(locals) - Frames.putAllS(argsS) - } + Frames.putAllS(argsS) callee(newMKont) } case Import("console", "log", _) | Import("spectest", "print_i32", _) => //println(s"[DEBUG] current stack: $stack") - val (ty, ct2) = ct1.pop() + val (ty, newCtx) = ctx.pop() val v = Stack.popC(ty) Stack.popS(ty) println(v.toInt) - eval(rest, kont, mkont, trail)(ct2) + eval(rest, kont, mkont, trail)(newCtx) case Import("console", "assert", _) => - val (ty, ct2) = ct1.pop() + val (ty, newCtx) = ctx.pop() val v = Stack.popC(ty) // TODO: We should also add s into exploration tree val s = Stack.popS(ty) runtimeAssert(v.toInt != 0) - eval(rest, kont, mkont, trail)(ct2) + eval(rest, kont, mkont, trail)(newCtx) case Import(_, _, _) => throw new Exception(s"Unknown import at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } @@ -811,7 +614,7 @@ trait StagedWasmEvaluator extends SAIOps { resetStacks() Frames.pushFrameC(locals) Frames.pushFrameS(locals) - eval(instrs, _ => forwardKont, mkont, ((_: CleanCT) => forwardKont)::Nil)(CleanCT(Context(Nil, locals))) + eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) Frames.popFrameC(locals.size) Frames.popFrameS(locals.size) } @@ -1074,8 +877,8 @@ trait StagedWasmEvaluator extends SAIOps { // Exploration tree, object ExploreTree { - def fillWithIfElse(sym: Rep[SymVal], snapshot: Rep[Snapshot]): Rep[Unit] = { - "tree-fill-if-else".reflectCtrlWith[Unit](sym, snapshot) + def fillWithIfElse(s: Rep[SymVal]): Rep[Unit] = { + "tree-fill-if-else".reflectCtrlWith[Unit](s) } def fillWithFinished(): Rep[Unit] = { @@ -1102,20 +905,6 @@ trait StagedWasmEvaluator extends SAIOps { } } - object ReuseManager { - def isReusing: Rep[Boolean] = { - "reuse-is-reusing".reflectCtrlWith[Boolean]() - } - - def turnOnReuse(): Rep[Unit] = { - "reuse-turn-on".reflectCtrlWith[Unit]() - } - - def turnOffReuse(): Rep[Unit] = { - "reuse-turn-off".reflectCtrlWith[Unit]() - } - } - // runtime Num type implicit class StagedConcreteNumOps(num: StagedConcreteNum) { @@ -1624,8 +1413,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("SymEnv.read("); shallow(sym); emit(")") case Node(_, "assert-true", List(cond), _) => emit("GENSYM_ASSERT("); shallow(cond); emit(")") - case Node(_, "tree-fill-if-else", List(sym, snapshot), _) => - emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(", "); shallow(snapshot); emit(")") + case Node(_, "tree-fill-if-else", List(sym), _) => + emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(")") case Node(_, "tree-fill-finished", List(), _) => emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b), _) => @@ -1636,8 +1425,6 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.dump_graphviz("); shallow(f); emit(")") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") - case Node(_, "reuse-is-reusing", List(), _) => - emit("Reuse.is_reusing()") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => From 1bdb7da1a3d78e6e2e93be8f880f4f2ba0326d0d Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Fri, 29 Aug 2025 21:16:43 -0400 Subject: [PATCH 026/105] introduce a SnapshotNode, which currently behaves same as UnexploredNode --- headers/wasm/concolic_driver.hpp | 2 +- headers/wasm/symbolic_rt.hpp | 43 ++++++++++++++++--- .../scala/wasm/StagedConcolicMiniWasm.scala | 3 ++ 3 files changed, 41 insertions(+), 7 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 427a0de83..ab14525e2 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -38,8 +38,8 @@ class ManagedConcolicCleanup { }; inline void ConcolicDriver::run() { - ManagedConcolicCleanup cleanup{*this}; while (true) { + ManagedConcolicCleanup cleanup{*this}; ExploreTree.reset_cursor(); auto unexplored = ExploreTree.pick_unexplored(); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 6efa7cfe0..7931a3c33 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -273,7 +273,8 @@ struct NodeBox { std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); - + std::monostate fillSnapshotNode(); + bool isUnexplored() const; std::vector collect_path_conds(); }; @@ -384,6 +385,22 @@ struct UnExploredNode : Node { } }; +struct SnapshotNode : Node { + SnapshotNode() {} + std::string to_string() override { return "SnapshotNode"; } + +protected: + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "Snapshot", "box", "lightblue"); + + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } + } +}; + struct Finished : Node { Finished() {} std::string to_string() override { return "FinishedNode"; } @@ -439,7 +456,7 @@ inline NodeBox::NodeBox(NodeBox *parent) inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { // fill the current NodeBox with an ifelse branch node when it's unexplored - if (dynamic_cast(node.get())) { + if (this->isUnexplored()) { node = std::make_unique(cond, this); } assert( @@ -448,8 +465,15 @@ inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { return std::monostate(); } +inline std::monostate NodeBox::fillSnapshotNode() { + if (this->isUnexplored()) { + node = std::make_unique(); + } + return std::monostate(); +} + inline std::monostate NodeBox::fillFinishedNode() { - if (dynamic_cast(node.get())) { + if (this->isUnexplored()) { node = std::make_unique(); } else { assert(dynamic_cast(node.get()) != nullptr); @@ -458,7 +482,7 @@ inline std::monostate NodeBox::fillFinishedNode() { } inline std::monostate NodeBox::fillFailedNode() { - if (dynamic_cast(node.get())) { + if (this->isUnexplored()) { node = std::make_unique(); } else { assert(dynamic_cast(node.get()) != nullptr); @@ -467,7 +491,7 @@ inline std::monostate NodeBox::fillFailedNode() { } inline std::monostate NodeBox::fillUnreachableNode() { - if (dynamic_cast(node.get())) { + if (this->isUnexplored()) { node = std::make_unique(); } else { assert(dynamic_cast(node.get()) != nullptr); @@ -475,6 +499,11 @@ inline std::monostate NodeBox::fillUnreachableNode() { return std::monostate(); } +inline bool NodeBox::isUnexplored() const { + return dynamic_cast(node.get()) != nullptr || + dynamic_cast(node.get()) != nullptr; +} + inline std::vector NodeBox::collect_path_conds() { auto box = this; auto result = std::vector(); @@ -554,8 +583,10 @@ class ExploreTree_t { if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); if (branch) { + if_else_node->false_branch->fillSnapshotNode(); cursor = if_else_node->true_branch.get(); } else { + if_else_node->true_branch->fillSnapshotNode(); cursor = if_else_node->false_branch.get(); } @@ -599,7 +630,7 @@ class ExploreTree_t { private: NodeBox *pick_unexplored_of(NodeBox *node) { - if (dynamic_cast(node->node.get()) != nullptr) { + if (node->isUnexplored()) { return node; } auto if_else_node = dynamic_cast(node->node.get()); diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 7372ede92..d488e7d1c 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -404,6 +404,9 @@ trait StagedWasmEvaluator extends SAIOps { val cond = (label - toStagedNum(I32V(idx))).isZero() val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() ExploreTree.fillWithIfElse(condSym.s) + // When moving the cursor to a branch, we mark another branch as + // snapshotNode (this is done by moveCursor's runtime implementation) + // TODO: store snapshot into this snapshot node if (cond.toInt != 0) { ExploreTree.moveCursor(true) trail(choices.head)(newCtx)(mkont) From 64dce3263ad69956cd9636bab4f6787428e775ed Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 30 Aug 2025 14:11:56 -0400 Subject: [PATCH 027/105] fill snapshot into SnapshotNode --- headers/wasm/symbolic_rt.hpp | 27 +++--- .../scala/wasm/StagedConcolicMiniWasm.scala | 88 +++++++++++++------ 2 files changed, 76 insertions(+), 39 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 7931a3c33..e96adad96 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -228,7 +228,7 @@ class SymFrames_t { // A snapshot of the symbolic state and execution context (control) class Snapshot_t { public: - explicit Snapshot_t(); + explicit Snapshot_t(Cont_t cont, MCont_t mcont); SymStack_t get_stack() const { return stack; } SymFrames_t get_frames() const { return frames; } @@ -236,6 +236,9 @@ class Snapshot_t { private: SymStack_t stack; SymFrames_t frames; + // The continuation at the snapshot point + Cont_t cont; + MCont_t mcont; }; inline void SymStack_t::reuse(Snapshot_t snapshot) { @@ -273,7 +276,7 @@ struct NodeBox { std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); - std::monostate fillSnapshotNode(); + std::monostate fillSnapshotNode(Snapshot_t snapshot); bool isUnexplored() const; std::vector collect_path_conds(); }; @@ -386,7 +389,7 @@ struct UnExploredNode : Node { }; struct SnapshotNode : Node { - SnapshotNode() {} + SnapshotNode(Snapshot_t snapshot) : snapshot(snapshot) {} std::string to_string() override { return "SnapshotNode"; } protected: @@ -399,6 +402,9 @@ struct SnapshotNode : Node { graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); } } + +private: + Snapshot_t snapshot; }; struct Finished : Node { @@ -465,9 +471,9 @@ inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { return std::monostate(); } -inline std::monostate NodeBox::fillSnapshotNode() { +inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { if (this->isUnexplored()) { - node = std::make_unique(); + node = std::make_unique(snapshot); } return std::monostate(); } @@ -545,12 +551,11 @@ class Reuse_t { static Reuse_t Reuse; -inline Snapshot_t::Snapshot_t() : stack(SymStack), frames(SymFrames) { +inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont) + : stack(SymStack), frames(SymFrames), cont(cont), mcont(mcont) { #ifdef DEBUG std::cout << "Creating snapshot of size " << stack.size() << std::endl; #endif - assert(!Reuse.is_reusing() && - "Creating snapshot while reusing the symbolic stack"); } class ExploreTree_t { @@ -576,17 +581,17 @@ class ExploreTree_t { return cursor->fillIfElseNode(cond); } - std::monostate moveCursor(bool branch) { + std::monostate moveCursor(bool branch, Snapshot_t snapshot) { assert(cursor != nullptr); auto if_else_node = dynamic_cast(cursor->node.get()); assert( if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); if (branch) { - if_else_node->false_branch->fillSnapshotNode(); + if_else_node->false_branch->fillSnapshotNode(snapshot); cursor = if_else_node->true_branch.get(); } else { - if_else_node->true_branch->fillSnapshotNode(); + if_else_node->true_branch->fillSnapshotNode(snapshot); cursor = if_else_node->false_branch.get(); } diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index d488e7d1c..9b34bfba3 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -165,9 +165,9 @@ trait StagedWasmEvaluator extends SAIOps { trait Snapshot // Create a snapshot of the symbolic execution, we should ensure that current symstack is in use - // We don't need to store the control information, since the control is totally decided by concrete states - def makeSnapshot(): Rep[Snapshot] = { - "snapshot-make".reflectCtrlWith[Snapshot]() + // We need to store the control information, so we can resume the execution later + def makeSnapshot(kont: Rep[Cont[Unit]], mkont: Rep[MCont[Unit]]): Rep[Snapshot] = { + "snapshot-make".reflectCtrlWith[Snapshot](kont, mkont) } def eval(insts: List[Instr], @@ -365,14 +365,23 @@ trait StagedWasmEvaluator extends SAIOps { val newRestCtx = restCtx.shift(offset, funcTy.out.size) eval(rest, kont, mk, trail)(newRestCtx) }) - // TODO: put the cond.s to path condition ExploreTree.fillWithIfElse(symCond.s) + def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info("Entering the true branch of the if") + eval(thn, restK _, mk, restK _ :: trail)(newCtx) + }) + def elsK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info("Entering the false branch of the if") + eval(els, restK _, mk, restK _ :: trail)(newCtx) + }) if (cond.toInt != 0) { - ExploreTree.moveCursor(true) - eval(thn, restK _, mkont, restK _ :: trail)(newCtx) + val snapshot = makeSnapshot(elsK, mkont) + ExploreTree.moveCursor(true, snapshot) + thnK(mkont) } else { - ExploreTree.moveCursor(false) - eval(els, restK _, mkont, restK _ :: trail)(newCtx) + val snapshot = makeSnapshot(thnK, mkont) + ExploreTree.moveCursor(false, snapshot) + elsK(mkont) } () case Br(label) => @@ -384,40 +393,63 @@ trait StagedWasmEvaluator extends SAIOps { val symCond = Stack.popS(ty) info(s"The br_if(${label})'s condition is ", cond.toInt) ExploreTree.fillWithIfElse(symCond.s) + def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + trail(label)(newCtx)(mk) + }) + def elsK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + eval(rest, kont, mk, trail)(newCtx) + }) if (cond.toInt != 0) { info(s"Jump to $label") - ExploreTree.moveCursor(true) - trail(label)(newCtx)(mkont) + val snapshot = makeSnapshot(elsK, mkont) + ExploreTree.moveCursor(true, snapshot) + thnK(mkont) } else { info(s"Continue") - ExploreTree.moveCursor(false) - eval(rest, kont, mkont, trail)(newCtx) + val snapshot = makeSnapshot(thnK, mkont) + ExploreTree.moveCursor(false, snapshot) + elsK(mkont) } () case BrTable(labels, default) => val (ty, newCtx) = ctx.pop() - val label = Stack.popC(ty) - val labelSym = Stack.popS(ty) - def aux(choices: List[Int], idx: Int): Rep[Unit] = { - if (choices.isEmpty) trail(default)(newCtx)(mkont) - else { + def aux(choices: List[Int], idx: Int, mkont: Rep[MCont[Unit]]): Rep[Unit] = { + if (choices.isEmpty) { + Stack.popC(ty) + Stack.popS(ty) + trail(default)(newCtx)(mkont) + } else { + val label = Stack.peekC(ty) + val labelSym = Stack.peekS(ty) val cond = (label - toStagedNum(I32V(idx))).isZero() val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() ExploreTree.fillWithIfElse(condSym.s) // When moving the cursor to a branch, we mark another branch as // snapshotNode (this is done by moveCursor's runtime implementation) // TODO: store snapshot into this snapshot node + def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info("Entering the true branch of the br_table") + Stack.popC(ty) + Stack.popS(ty) + trail(choices.head)(newCtx)(mk) + }) + def elsK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info("Entering the false branch of the br_table") + aux(choices.tail, idx + 1, mk) + }) if (cond.toInt != 0) { - ExploreTree.moveCursor(true) - trail(choices.head)(newCtx)(mkont) + val snapshot = makeSnapshot(elsK, mkont) + ExploreTree.moveCursor(true, snapshot) + thnK(mkont) } else { - ExploreTree.moveCursor(false) - aux(choices.tail, idx + 1) + val snapshot = makeSnapshot(thnK, mkont) + ExploreTree.moveCursor(false, snapshot) + elsK(mkont) } } } - aux(labels, 0) + aux(labels, 0, mkont) case Return => trail.last(ctx)(mkont) case Call(f) => evalCall(rest, kont, mkont, trail, f, false) case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) @@ -888,9 +920,9 @@ trait StagedWasmEvaluator extends SAIOps { "tree-fill-finished".reflectCtrlWith[Unit]() } - def moveCursor(branch: Boolean): Rep[Unit] = { + def moveCursor(branch: Boolean, snapshot: Rep[Snapshot]): Rep[Unit] = { // when moving cursor from to an unexplored node, we need to change the reuse state - "tree-move-cursor".reflectCtrlWith[Unit](branch) + "tree-move-cursor".reflectCtrlWith[Unit](branch, snapshot) } def print(): Rep[Unit] = { @@ -1323,8 +1355,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.pop()") case Node(_, "sym-stack-pop", _, _) => emit("SymStack.pop()") - case Node(_, "snapshot-make", _, _) => - emit("Snapshot_t()") + case Node(_, "snapshot-make", List(k, mk), _) => + emit("Snapshot_t("); shallow(k); emit(", "); shallow(mk); emit(")") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(")") case Node(_, "sym-frame-pop", List(i), _) => @@ -1420,8 +1452,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(")") case Node(_, "tree-fill-finished", List(), _) => emit("ExploreTree.fillFinishedNode()") - case Node(_, "tree-move-cursor", List(b), _) => - emit("ExploreTree.moveCursor("); shallow(b); emit(")") + case Node(_, "tree-move-cursor", List(b, snapshot), _) => + emit("ExploreTree.moveCursor("); shallow(b); emit(", "); shallow(snapshot); emit(")") case Node(_, "tree-print", List(), _) => emit("ExploreTree.print()") case Node(_, "tree-dump-graphviz", List(f), _) => From 463871cf3c5ce2f30cb64fa3856f92f263c99a56 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 31 Aug 2025 16:36:53 -0400 Subject: [PATCH 028/105] snapshot reuse via continuation more tests should be added --- headers/wasm/concolic_driver.hpp | 12 +- headers/wasm/concrete_rt.hpp | 24 +++ headers/wasm/controls.hpp | 9 +- headers/wasm/symbolic_rt.hpp | 157 ++++++++++++++---- .../genwasym/TestStagedConcolicEval.scala | 6 +- 5 files changed, 172 insertions(+), 36 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index ab14525e2..1c2fcc2e7 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -38,9 +38,9 @@ class ManagedConcolicCleanup { }; inline void ConcolicDriver::run() { + ExploreTree.reset_cursor(); while (true) { ManagedConcolicCleanup cleanup{*this}; - ExploreTree.reset_cursor(); auto unexplored = ExploreTree.pick_unexplored(); if (!unexplored) { @@ -55,11 +55,19 @@ inline void ConcolicDriver::run() { continue; } auto new_env = result.value(); + + // update global symbolic environment from SMT solved model SymEnv.update(std::move(new_env)); try { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); - entrypoint(); + if (auto snapshot_node = + dynamic_cast(unexplored->node.get())) { + snapshot_node->get_snapshot().resume_execution(SymEnv, unexplored); + } else { + entrypoint(); + } + GENSYM_INFO("Execution finished successfully with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); } catch (...) { diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index a9abccf2d..16642067c 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -1,6 +1,7 @@ #ifndef WASM_CONCRETE_RT_HPP #define WASM_CONCRETE_RT_HPP +#include "wasm/utils.hpp" #include #include #include @@ -120,6 +121,16 @@ class Stack_t { void reset() { count = 0; } + void resize(int32_t new_size) { + assert(new_size >= 0); + count = new_size; + } + + void set_from_front(int32_t index, const Num &num) { + assert(index >= 0 && index < count); + stack_ptr[index] = num; + } + private: int32_t count; Num *stack_ptr; @@ -152,6 +163,19 @@ class Frames_t { void reset() { count = 0; } + size_t size() const { return count; } + + void set_from_front(int32_t index, const Num &num) { + GENSYM_DBG(index); + assert(index >= 0 && index < count && "Index out of bounds"); + stack_ptr[index] = num; + } + + void resize(int32_t new_size) { + assert(new_size >= 0); + count = new_size; + } + private: int32_t count; Num *stack_ptr; diff --git a/headers/wasm/controls.hpp b/headers/wasm/controls.hpp index 16fa5136a..513f06924 100644 --- a/headers/wasm/controls.hpp +++ b/headers/wasm/controls.hpp @@ -1,5 +1,12 @@ + +#ifndef WASM_CONTROLS_HPP +#define WASM_CONTROLS_HPP + #include + #include using MCont_t = std::function; -using Cont_t = std::function; \ No newline at end of file +using Cont_t = std::function; + +#endif // WASM_CONTROLS_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index e96adad96..d18ea6093 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -3,6 +3,7 @@ #include "concrete_rt.hpp" #include "controls.hpp" +#include "utils.hpp" #include #include #include @@ -71,6 +72,8 @@ struct SymVal { SymVal gt(const SymVal &other) const; SymVal geq(const SymVal &other) const; SymVal negate() const; + + bool is_concrete() const; }; static SymVal make_symbolic(int index) { @@ -145,6 +148,10 @@ inline SymVal SymVal::makeSymbolic() const { } } +inline bool SymVal::is_concrete() const { + return dynamic_cast(symptr.get()) != nullptr; +} + class Snapshot_t; class SymStack_t { @@ -186,6 +193,8 @@ class SymStack_t { size_t size() const { return stack.size(); } + SymVal operator[](size_t index) const { return stack[index]; } + private: std::vector stack; }; @@ -222,9 +231,17 @@ class SymFrames_t { void reuse(Snapshot_t snapshot); + size_t size() const { return stack.size(); } + + SymVal operator[](size_t index) const { return stack[index]; } + +private: std::vector stack; }; +struct NodeBox; +struct SymEnv_t; + // A snapshot of the symbolic state and execution context (control) class Snapshot_t { public: @@ -233,6 +250,8 @@ class Snapshot_t { SymStack_t get_stack() const { return stack; } SymFrames_t get_frames() const { return frames; } + std::monostate resume_execution(SymEnv_t &sym_env, NodeBox *node) const; + private: SymStack_t stack; SymFrames_t frames; @@ -391,6 +410,7 @@ struct UnExploredNode : Node { struct SnapshotNode : Node { SnapshotNode(Snapshot_t snapshot) : snapshot(snapshot) {} std::string to_string() override { return "SnapshotNode"; } + const Snapshot_t &get_snapshot() const { return snapshot; } protected: void generate_dot(std::ostream &os, int parent_dot_id, @@ -479,6 +499,7 @@ inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { } inline std::monostate NodeBox::fillFinishedNode() { + GENSYM_DBG("Filling with a Finished Node"); if (this->isUnexplored()) { node = std::make_unique(); } else { @@ -491,6 +512,11 @@ inline std::monostate NodeBox::fillFailedNode() { if (this->isUnexplored()) { node = std::make_unique(); } else { + if (auto if_else_node = dynamic_cast(node.get())) { + GENSYM_DBG(typeid(*if_else_node).name()); + } else if (auto finished_node = dynamic_cast(node.get())) { + GENSYM_DBG(typeid(*finished_node).name()); + } assert(dynamic_cast(node.get()) != nullptr); } return std::monostate(); @@ -533,24 +559,6 @@ inline std::vector NodeBox::collect_path_conds() { return result; } -class Reuse_t { -public: - Reuse_t() : reuse_flag(false) {} - bool is_reusing() { - // we are in reuse mode and the flag is set - return REUSE_MODE && reuse_flag; - } - - void turn_on_reusing() { reuse_flag = true; } - - void turn_off_reusing() { reuse_flag = false; } - -private: - bool reuse_flag; -}; - -static Reuse_t Reuse; - inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont) : stack(SymStack), frames(SymFrames), cont(cont), mcont(mcont) { #ifdef DEBUG @@ -564,13 +572,15 @@ class ExploreTree_t { : root(std::make_unique(nullptr)), cursor(root.get()) {} void reset_cursor() { + GENSYM_INFO("Resetting cursor to root"); // Reset the cursor to the root of the tree cursor = root.get(); - Reuse.turn_off_reusing(); - // if root cursor is a branch node, then we can reuse the snapshot inside it - if (auto ite = dynamic_cast(cursor->node.get())) { - Reuse.turn_on_reusing(); - } + } + + void set_cursor(NodeBox *new_cursor) { + GENSYM_INFO("Setting cursor to a new node"); + cursor = new_cursor; + assert(dynamic_cast(cursor->node.get()) != nullptr); } std::monostate fillFinishedNode() { return cursor->fillFinishedNode(); } @@ -656,18 +666,23 @@ static ExploreTree_t ExploreTree; class SymEnv_t { public: - Num read(SymVal sym) { - auto symbol = dynamic_cast(sym.symptr.get()); - assert(symbol); - if (symbol->get_id() >= map.size()) { - map.resize(symbol->get_id() + 1); + Num read(const Symbol &symbol) { + if (symbol.get_id() >= map.size()) { + map.resize(symbol.get_id() + 1); } #if DEBUG - std::cout << "Read symbol: " << symbol->get_id() + std::cout << "Read symbol: " << symbol.get_id() << " from symbolic environment" << std::endl; std::cout << "Current symbolic environment: " << to_string() << std::endl; #endif - return map[symbol->get_id()]; + + return map[symbol.get_id()]; + } + + Num read(SymVal sym) { + auto symbol = dynamic_cast(sym.symptr.get()); + assert(symbol); + return read(*symbol); } void update(std::vector new_env) { map = std::move(new_env); } @@ -684,10 +699,92 @@ class SymEnv_t { return result; } + size_t size() const { return map.size(); } + private: std::vector map; // The symbolic environment, a vector of Num }; static SymEnv_t SymEnv; +// TODO: reduce the re-computation of the same symbolic expression, it's better +// if it can be done by the smt solver +static Num eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { + if (auto concrete = dynamic_cast(sym.symptr.get())) { + return concrete->value; + } else if (auto operation = dynamic_cast(sym.symptr.get())) { + // If it's a operation, we need to evaluate it + auto lhs = eval_sym_expr(operation->lhs, sym_env); + auto rhs = eval_sym_expr(operation->rhs, sym_env); + switch (operation->op) { + case ADD: + return lhs + rhs; + case SUB: + return lhs - rhs; + case MUL: + return lhs * rhs; + case DIV: + return lhs / rhs; + case LT: + return lhs < rhs; + case LEQ: + return lhs <= rhs; + case GT: + return lhs > rhs; + case GEQ: + return lhs >= rhs; + default: + throw std::runtime_error("Operation not supported: " + + std::to_string(operation->op)); + } + } else if (auto symbol = dynamic_cast(sym.symptr.get())) { + auto sym_id = symbol->get_id(); + GENSYM_INFO("Reading symbol: " + std::to_string(sym_id)); + return sym_env.read(sym); + } + throw std::runtime_error("Not supported symbolic expression"); +} + +static void resume_conc_stack(const SymStack_t &sym_stack, Stack_t &stack, + SymEnv_t &sym_env) { + stack.resize(sym_stack.size()); + for (size_t i = 0; i < sym_stack.size(); ++i) { + auto sym = sym_stack[i]; + auto conc = eval_sym_expr(sym, sym_env); + stack.set_from_front(i, conc); + } +} + +static void resume_conc_frames(const SymFrames_t &sym_frame, Frames_t &frames, + SymEnv_t &sym_env) { + frames.resize(sym_frame.size()); + for (size_t i = 0; i < sym_frame.size(); ++i) { + auto sym = sym_frame[i]; + auto conc = eval_sym_expr(sym, sym_env); + frames.set_from_front(i, conc); + } +} + +static void resume_conc_states(const SymStack_t &sym_stack, + const SymFrames_t &sym_frame, Stack_t &stack, + Frames_t &frames, SymEnv_t &sym_env) { + resume_conc_stack(sym_stack, stack, sym_env); + resume_conc_frames(sym_frame, frames, sym_env); +} + +inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, + NodeBox *node) const { + // Reset explore tree's cursor + ExploreTree.set_cursor(node); + + // Restore the symbolic state from the snapshot + GENSYM_INFO("Reusing symbolic state from snapshot"); + SymStack = stack; + SymFrames = frames; + // Restore the concrete states from the symbolic states + resume_conc_states(stack, frames, Stack, Frames, sym_env); + // Resume execution from the continuation + return cont(mcont); +} + #endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 48c246342..5a77f58d6 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -42,13 +42,13 @@ class TestStagedConcolicEval extends FunSuite { }) } - test("ack-cpp") { testFileConcolicCpp("./benchmarks/wasm/ack.wat", Some("real_main")) } + test("ack-cpp-concolic") { testFileConcolicCpp("./benchmarks/wasm/ack.wat", Some("real_main")) } - test("bug-finding") { + test("bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main")) } - test("brtable-bug-finding") { + test("brtable-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/staged/brtable_concolic.wat") } From 261c650e78956204ae4b190e7841b27e97a0084f Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 1 Sep 2025 13:28:40 -0400 Subject: [PATCH 029/105] remove debug printings --- headers/wasm/concrete_rt.hpp | 1 - headers/wasm/symbolic_rt.hpp | 6 ------ 2 files changed, 7 deletions(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 16642067c..76c2537a2 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -166,7 +166,6 @@ class Frames_t { size_t size() const { return count; } void set_from_front(int32_t index, const Num &num) { - GENSYM_DBG(index); assert(index >= 0 && index < count && "Index out of bounds"); stack_ptr[index] = num; } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index d18ea6093..730e778be 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -499,7 +499,6 @@ inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { } inline std::monostate NodeBox::fillFinishedNode() { - GENSYM_DBG("Filling with a Finished Node"); if (this->isUnexplored()) { node = std::make_unique(); } else { @@ -512,11 +511,6 @@ inline std::monostate NodeBox::fillFailedNode() { if (this->isUnexplored()) { node = std::make_unique(); } else { - if (auto if_else_node = dynamic_cast(node.get())) { - GENSYM_DBG(typeid(*if_else_node).name()); - } else if (auto finished_node = dynamic_cast(node.get())) { - GENSYM_DBG(typeid(*finished_node).name()); - } assert(dynamic_cast(node.get()) != nullptr); } return std::monostate(); From 1c6a0452bf41479c861a9d4f2fada72edad5574a Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 3 Sep 2025 20:37:19 -0400 Subject: [PATCH 030/105] give every branch node an ID --- headers/wasm/concolic_driver.hpp | 2 +- headers/wasm/symbolic_rt.hpp | 15 +++---- .../scala/wasm/StagedConcolicMiniWasm.scala | 42 +++++++++++++++---- 3 files changed, 42 insertions(+), 17 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 1c2fcc2e7..e0b9e7264 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -100,7 +100,7 @@ static void start_concolic_execution_with( } static void start_concolic_execution_with( - std::function entrypoint) { + std::function entrypoint, int branchCount) { const char *env_tree_file = std::getenv("TREE_FILE"); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 730e778be..dfc0f7b1a 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -291,7 +291,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond); + std::monostate fillIfElseNode(SymVal cond, int id); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -344,10 +344,11 @@ struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; + int id; - IfElseNode(SymVal cond, NodeBox *parent) + IfElseNode(SymVal cond, NodeBox *parent, int id) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)) {} + false_branch(std::make_unique(parent)), id(id) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -480,10 +481,10 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { +inline std::monostate NodeBox::fillIfElseNode(SymVal cond, int id) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (this->isUnexplored()) { - node = std::make_unique(cond, this); + node = std::make_unique(cond, this, id); } assert( dynamic_cast(node.get()) != nullptr && @@ -581,8 +582,8 @@ class ExploreTree_t { std::monostate fillFailedNode() { return cursor->fillFailedNode(); } - std::monostate fillIfElseNode(SymVal cond) { - return cursor->fillIfElseNode(cond); + std::monostate fillIfElseNode(SymVal cond, int id) { + return cursor->fillIfElseNode(cond, id); } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 9b34bfba3..5630e18da 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -19,6 +19,26 @@ import gensym.wasm.symbolic.Concrete import gensym.wasm.symbolic.ExploreTree import gensym.structure.freer.Explore +object Counter { + var currentId: Int = 0 + private val dict = new HashMap[WIR, Int]() + + def reset(): Unit = { + currentId = 0 + dict.clear() + } + + def getId(wir: WIR): Int = { + if (dict.contains(wir)) { + dict(wir) + } else { + val id = currentId + currentId += 1 + dict(wir) = id + id + } + } +} @virtualize trait StagedWasmEvaluator extends SAIOps { def module: ModuleInstance @@ -365,7 +385,8 @@ trait StagedWasmEvaluator extends SAIOps { val newRestCtx = restCtx.shift(offset, funcTy.out.size) eval(rest, kont, mk, trail)(newRestCtx) }) - ExploreTree.fillWithIfElse(symCond.s) + val id = Counter.getId(inst) + ExploreTree.fillWithIfElse(symCond.s, id) def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info("Entering the true branch of the if") eval(thn, restK _, mk, restK _ :: trail)(newCtx) @@ -392,7 +413,8 @@ trait StagedWasmEvaluator extends SAIOps { val cond = Stack.popC(ty) val symCond = Stack.popS(ty) info(s"The br_if(${label})'s condition is ", cond.toInt) - ExploreTree.fillWithIfElse(symCond.s) + val id = Counter.getId(inst) + ExploreTree.fillWithIfElse(symCond.s, id) def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { trail(label)(newCtx)(mk) }) @@ -423,7 +445,8 @@ trait StagedWasmEvaluator extends SAIOps { val labelSym = Stack.peekS(ty) val cond = (label - toStagedNum(I32V(idx))).isZero() val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() - ExploreTree.fillWithIfElse(condSym.s) + val id = Counter.getId(inst) + ExploreTree.fillWithIfElse(condSym.s, id) // When moving the cursor to a branch, we mark another branch as // snapshotNode (this is done by moveCursor's runtime implementation) // TODO: store snapshot into this snapshot node @@ -622,6 +645,7 @@ trait StagedWasmEvaluator extends SAIOps { } def evalTop(mkont: Rep[MCont[Unit]], main: Option[String]): Rep[Unit] = { + Counter.reset() val funBody: FuncBodyDef = main match { case Some(func_name) => module.defs.flatMap({ @@ -912,8 +936,8 @@ trait StagedWasmEvaluator extends SAIOps { // Exploration tree, object ExploreTree { - def fillWithIfElse(s: Rep[SymVal]): Rep[Unit] = { - "tree-fill-if-else".reflectCtrlWith[Unit](s) + def fillWithIfElse(s: Rep[SymVal], id: Int): Rep[Unit] = { + "tree-fill-if-else".reflectCtrlWith[Unit](s, id) } def fillWithFinished(): Rep[Unit] = { @@ -1448,8 +1472,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("SymEnv.read("); shallow(sym); emit(")") case Node(_, "assert-true", List(cond), _) => emit("GENSYM_ASSERT("); shallow(cond); emit(")") - case Node(_, "tree-fill-if-else", List(sym), _) => - emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(")") + case Node(_, "tree-fill-if-else", List(sym, id), _) => + emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(", "); emit(id.toString); emit(")") case Node(_, "tree-fill-finished", List(), _) => emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b, snapshot), _) => @@ -1496,12 +1520,12 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emitDatastructures(stream) emitFunctions(stream) emit(src) - emitln(""" + emitln(s""" |/***************************************** |End of Generated Code |*******************************************/ |int main(int argc, char *argv[]) { - | start_concolic_execution_with(Snippet); + | start_concolic_execution_with(Snippet, ${Counter.currentId}); | return 0; |}""".stripMargin) } From 8971eb54fd9740925cc23243b38ff7233a92613e Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 3 Sep 2025 21:22:51 -0400 Subject: [PATCH 031/105] a bitmap to record the branch coverage --- headers/wasm/concolic_driver.hpp | 26 +++++++++++--------------- headers/wasm/symbolic_rt.hpp | 22 +++++++++++++++------- 2 files changed, 26 insertions(+), 22 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index e0b9e7264..83252f7dd 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -6,6 +6,7 @@ #include "symbolic_rt.hpp" #include "utils.hpp" #include +#include #include #include #include @@ -14,10 +15,11 @@ class ConcolicDriver { friend class ManagedConcolicCleanup; public: - ConcolicDriver(std::function entrypoint, std::string tree_file) - : entrypoint(entrypoint), tree_file(tree_file) {} - ConcolicDriver(std::function entrypoint) - : entrypoint(entrypoint), tree_file(std::nullopt) {} + ConcolicDriver(std::function entrypoint, + std::optional tree_file, int branchCount) + : entrypoint(entrypoint), tree_file(tree_file) { + ExploreTree.branch_cov_map.assign(branchCount, false); + } void run(); private: @@ -92,22 +94,16 @@ static std::monostate reset_stacks() { return std::monostate{}; } -static void start_concolic_execution_with( - std::function entrypoint, - std::string tree_file) { - ConcolicDriver driver([=]() { entrypoint(std::monostate{}); }, tree_file); - driver.run(); -} - static void start_concolic_execution_with( std::function entrypoint, int branchCount) { const char *env_tree_file = std::getenv("TREE_FILE"); - ConcolicDriver driver = - env_tree_file ? ConcolicDriver([=]() { entrypoint(std::monostate{}); }, - env_tree_file) - : ConcolicDriver([=]() { entrypoint(std::monostate{}); }); + auto tree_file = + env_tree_file ? std::make_optional(env_tree_file) : std::nullopt; + + ConcolicDriver driver = ConcolicDriver( + [=]() { entrypoint(std::monostate{}); }, tree_file, branchCount); driver.run(); } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index dfc0f7b1a..1d80b0376 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -291,7 +291,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond, int id); + std::monostate fillIfElseNode(SymVal cond); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -344,11 +344,10 @@ struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; - int id; - IfElseNode(SymVal cond, NodeBox *parent, int id) + IfElseNode(SymVal cond, NodeBox *parent) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)), id(id) {} + false_branch(std::make_unique(parent)) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -481,10 +480,10 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond, int id) { +inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (this->isUnexplored()) { - node = std::make_unique(cond, this, id); + node = std::make_unique(cond, this); } assert( dynamic_cast(node.get()) != nullptr && @@ -583,7 +582,8 @@ class ExploreTree_t { std::monostate fillFailedNode() { return cursor->fillFailedNode(); } std::monostate fillIfElseNode(SymVal cond, int id) { - return cursor->fillIfElseNode(cond, id); + branch_cov_map[id] = true; + return cursor->fillIfElseNode(cond); } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { @@ -637,6 +637,14 @@ class ExploreTree_t { // For now, we just iterate through the tree and return the first unexplored return pick_unexplored_of(root.get()); } + std::vector branch_cov_map; + bool all_branch_covered() const { + for (bool covered : branch_cov_map) { + if (!covered) + return false; + } + return true; + } private: NodeBox *pick_unexplored_of(NodeBox *node) { From 1b92fc0e8db85ac4b567fe121e23dd970aa178d4 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 4 Sep 2025 13:00:17 -0400 Subject: [PATCH 032/105] a new exploring strategy: exit when all branches are covered --- headers/wasm/concolic_driver.hpp | 23 +++++++++++++++-- headers/wasm/symbolic_rt.hpp | 25 ++++++++++++------- .../scala/wasm/StagedConcolicMiniWasm.scala | 20 ++++++++++----- .../genwasym/TestStagedConcolicEval.scala | 14 +++++++++-- 4 files changed, 63 insertions(+), 19 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 83252f7dd..0ad212465 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -11,6 +11,16 @@ #include #include +enum class ExploreMode { EarlyExit, ExitByCoverage }; + +#ifdef EARLY_EXIT +static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; +#elif defined(BY_COVERAGE) +static const ExploreMode EXPLORE_MODE = ExploreMode::ExitByCoverage; +#else +static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; +#endif + class ConcolicDriver { friend class ManagedConcolicCleanup; @@ -18,7 +28,8 @@ class ConcolicDriver { ConcolicDriver(std::function entrypoint, std::optional tree_file, int branchCount) : entrypoint(entrypoint), tree_file(tree_file) { - ExploreTree.branch_cov_map.assign(branchCount, false); + ExploreTree.true_branch_cov_map.assign(branchCount, false); + ExploreTree.false_branch_cov_map.assign(branchCount, false); } void run(); @@ -76,7 +87,15 @@ inline void ConcolicDriver::run() { ExploreTree.fillFailedNode(); GENSYM_INFO("Caught runtime error with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); - return; + switch (EXPLORE_MODE) { + case ExploreMode::EarlyExit: + return; + case ExploreMode::ExitByCoverage: + if (ExploreTree.all_branch_covered()) { + GENSYM_INFO("All branches covered, exiting..."); + return; + } + } } #if defined(RUN_ONCE) return; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 1d80b0376..974a71c7f 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -291,7 +291,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond); + std::monostate fillIfElseNode(SymVal cond, int id); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -344,10 +344,11 @@ struct IfElseNode : Node { SymVal cond; std::unique_ptr true_branch; std::unique_ptr false_branch; + int id; - IfElseNode(SymVal cond, NodeBox *parent) + IfElseNode(SymVal cond, NodeBox *parent, int id) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)) {} + false_branch(std::make_unique(parent)), id(id) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -480,10 +481,10 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond) { +inline std::monostate NodeBox::fillIfElseNode(SymVal cond, int id) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (this->isUnexplored()) { - node = std::make_unique(cond, this); + node = std::make_unique(cond, this, id); } assert( dynamic_cast(node.get()) != nullptr && @@ -582,8 +583,7 @@ class ExploreTree_t { std::monostate fillFailedNode() { return cursor->fillFailedNode(); } std::monostate fillIfElseNode(SymVal cond, int id) { - branch_cov_map[id] = true; - return cursor->fillIfElseNode(cond); + return cursor->fillIfElseNode(cond, id); } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { @@ -593,9 +593,11 @@ class ExploreTree_t { if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); if (branch) { + true_branch_cov_map[if_else_node->id] = true; if_else_node->false_branch->fillSnapshotNode(snapshot); cursor = if_else_node->true_branch.get(); } else { + false_branch_cov_map[if_else_node->id] = true; if_else_node->true_branch->fillSnapshotNode(snapshot); cursor = if_else_node->false_branch.get(); } @@ -637,9 +639,14 @@ class ExploreTree_t { // For now, we just iterate through the tree and return the first unexplored return pick_unexplored_of(root.get()); } - std::vector branch_cov_map; + std::vector true_branch_cov_map; + std::vector false_branch_cov_map; bool all_branch_covered() const { - for (bool covered : branch_cov_map) { + for (bool covered : true_branch_cov_map) { + if (!covered) + return false; + } + for (bool covered : false_branch_cov_map) { if (!covered) return false; } diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 5630e18da..118b59491 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -21,22 +21,30 @@ import gensym.structure.freer.Explore object Counter { var currentId: Int = 0 - private val dict = new HashMap[WIR, Int]() + + // WIR is the branch's corresponding ast, while the Int stands for the nth + // branch of the AST(a WIR may contain multiple branches, e.g., br_table) + private val dict = new HashMap[(WIR, Int), Int]() def reset(): Unit = { currentId = 0 dict.clear() } - def getId(wir: WIR): Int = { - if (dict.contains(wir)) { - dict(wir) + def getId(wir: WIR, nth: Int = 0): Int = { + if (dict.contains((wir, nth))) { + dict((wir, nth)) } else { val id = currentId currentId += 1 - dict(wir) = id + dict((wir, nth)) = id id } + + } + + def getId(wir: WIR): Int = { + getId(wir, 0) } } @virtualize @@ -445,7 +453,7 @@ trait StagedWasmEvaluator extends SAIOps { val labelSym = Stack.peekS(ty) val cond = (label - toStagedNum(I32V(idx))).isZero() val condSym = (labelSym - toStagedSymbolicNum(I32V(idx))).isZero() - val id = Counter.getId(inst) + val id = Counter.getId(inst, idx) ExploreTree.fillWithIfElse(condSym.s, id) // When moving the cursor to a branch, we mark another branch as // snapshotNode (this is done by moveCursor's runtime implementation) diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 5a77f58d6..0e0019ee6 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -9,12 +9,14 @@ import gensym.wasm.parser._ import gensym.wasm.stagedconcolicminiwasm._ class TestStagedConcolicEval extends FunSuite { - def testFileConcolicCpp(filename: String, main: Option[String] = None) = { + def testFileConcolicCpp(filename: String, + main: Option[String] = None, + exitByCoverage: Boolean = false) = { val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" val exe = s"$cppFile.exe" val exploreTreeFile = s"$filename.tree.dot" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true) + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") import sys.process._ val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! @@ -52,6 +54,14 @@ class TestStagedConcolicEval extends FunSuite { testFileConcolicCpp("./benchmarks/wasm/staged/brtable_concolic.wat") } + test("bug-finding-cov-concolic") { + testFileConcolicCpp("./benchmarks/wasm/branch-strip-buggy.wat", Some("real_main"), exitByCoverage=true) + } + + test("brtable-bug-finding-cov-concolic") { + testFileConcolicCpp("./benchmarks/wasm/staged/brtable_concolic.wat", exitByCoverage=true) + } + test("return-poly - concrete") { testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) } From 0f7ca5a5ea02d870147f6e3b23dfc2c576e5419d Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 7 Sep 2025 16:25:15 -0400 Subject: [PATCH 033/105] support numeric globals --- benchmarks/wasm/staged/simple_global.wat | 22 +++++++++++++ headers/wasm/concolic_driver.hpp | 2 ++ headers/wasm/concrete_rt.hpp | 1 + headers/wasm/symbolic_rt.hpp | 1 + .../scala/wasm/StagedConcolicMiniWasm.scala | 32 +++++++++++++++++-- .../genwasym/TestStagedConcolicEval.scala | 4 +++ 6 files changed, 59 insertions(+), 3 deletions(-) create mode 100644 benchmarks/wasm/staged/simple_global.wat diff --git a/benchmarks/wasm/staged/simple_global.wat b/benchmarks/wasm/staged/simple_global.wat new file mode 100644 index 000000000..4877f42c4 --- /dev/null +++ b/benchmarks/wasm/staged/simple_global.wat @@ -0,0 +1,22 @@ +(module $simple_global + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (result i32))) + (type (;2;) (func (param i32))) + (func $real_main (type 1) (result i32) + (local i32) + i32.const 0 + i32.symbolic + local.tee 0 + local.get 0 + global.set 0 + if + else + i32.const 0 + call 1 + end) + (import "console" "assert" (func (type 2))) + (memory (;0;) 16) + (global $__stack_pointer (mut i32) (i32.const 1048576)) + (global (;1;) i32 (i32.const 1048576)) + (global (;2;) i32 (i32.const 1048576)) + (export "real_main" (func 0))) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 0ad212465..81b5d5ad8 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -94,6 +94,8 @@ inline void ConcolicDriver::run() { if (ExploreTree.all_branch_covered()) { GENSYM_INFO("All branches covered, exiting..."); return; + } else { + GENSYM_INFO("Found a bug, but not all branches covered, continuing..."); } } } diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 76c2537a2..179ef245e 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -181,6 +181,7 @@ class Frames_t { }; static Frames_t Frames; +static Frames_t Globals; static void initRand() { // for now, just do nothing diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 974a71c7f..137d071df 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -283,6 +283,7 @@ inline void SymFrames_t::reuse(Snapshot_t snapshot) { } static SymFrames_t SymFrames; +static SymFrames_t SymGlobals; struct Node; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 118b59491..a4958e277 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -679,6 +679,7 @@ trait StagedWasmEvaluator extends SAIOps { } val (instrs, locals) = (funBody.body, funBody.locals) resetStacks() + initGlobals(module.globals) Frames.pushFrameC(locals) Frames.pushFrameS(locals) eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) @@ -883,6 +884,18 @@ trait StagedWasmEvaluator extends SAIOps { "reset-stacks".reflectCtrlWith[Unit]() } + def initGlobals(globals: List[RTGlobal]): Rep[Unit] = { + Globals.reserveSpace(globals.size) + for ((g, i) <- globals.view.zipWithIndex) { + val initValue = g.value match { + case n: Num => n + case _ => throw new RuntimeException("Non-numeric global value is not supported yet") + } + Globals.setC(i, toStagedNum(initValue)) + Globals.setS(i, toStagedSymbolicNum(initValue)) + } + } + // call unreachable def unreachable(): Rep[Unit] = { "unreachable".reflectCtrlWith[Unit]() @@ -905,6 +918,11 @@ trait StagedWasmEvaluator extends SAIOps { // global read/write object Globals { + def reserveSpace(size: Int): Rep[Unit] = { + "global-reserve".reflectCtrlWith[Unit](size) + "sym-global-reserve".reflectCtrlWith[Unit](size) + } + def getC(i: Int): StagedConcreteNum = { module.globals(i).ty match { case GlobalType(NumType(I32Type), _) => I32C("global-get".reflectCtrlWith[Num](i)) @@ -1352,8 +1370,6 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Frames.set("); shallow(i); emit(", "); shallow(value); emit(");\n") case Node(_, "sym-frame-set", List(i, s_value), _) => emit("SymFrames.set("); shallow(i); emit(", "); shallow(s_value); emit(");\n") - case Node(_, "global-set", List(i, value), _) => - emit("Global.globalSet("); shallow(i); emit(", "); shallow(value); emit(");\n") // Note: The following code is copied from the traverse of CppBackend.scala, try to avoid duplicated code case n @ Node(f, "λ", (b: LMSBlock)::LMSConst(0)::rest, _) => // TODO: Is a leading block followed by 0 a hint for top function? @@ -1410,7 +1426,17 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "stack-size", _, _) => emit("Stack.size()") case Node(_, "global-get", List(i), _) => - emit("Global.globalGet("); shallow(i); emit(")") + emit("Globals.get("); shallow(i); emit(")") + case Node(_, "sym-global-get", List(i), _) => + emit("SymGlobal.get("); shallow(i); emit(")") + case Node(_, "global-set", List(i, value), _) => + emit("Globals.set("); shallow(i); emit(", "); shallow(value); emit(")") + case Node(_, "sym-global-set", List(i, s_value), _) => + emit("SymGlobals.set("); shallow(i); emit(", "); shallow(s_value); emit(")") + case Node(_, "global-reserve", List(i), _) => + emit("Globals.pushFrame("); shallow(i); emit(")") + case Node(_, "sym-global-reserve", List(i), _) => + emit("SymGlobals.pushFrame("); shallow(i); emit(")") case Node(_, "is-zero", List(num), _) => emit("(0 == "); shallow(num); emit(")") case Node(_, "sym-is-zero", List(s_num), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 0e0019ee6..303a3fe51 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -62,6 +62,10 @@ class TestStagedConcolicEval extends FunSuite { testFileConcolicCpp("./benchmarks/wasm/staged/brtable_concolic.wat", exitByCoverage=true) } + test("simple-global-bug-finding-cov-concolic") { + testFileConcolicCpp("./benchmarks/wasm/staged/simple_global.wat", Some("real_main"), exitByCoverage=true) + } + test("return-poly - concrete") { testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) } From 0fded4c6f34c1b16b10a3779ad42aa4675cfcc41 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 8 Sep 2025 20:00:47 -0400 Subject: [PATCH 034/105] Explicitly classify the next stage computation and its type Then we can compose/decompose them more easily. --- .../scala/wasm/StagedConcolicMiniWasm.scala | 596 +++++++++--------- 1 file changed, 288 insertions(+), 308 deletions(-) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index a4958e277..aee63cdad 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -51,60 +51,26 @@ object Counter { trait StagedWasmEvaluator extends SAIOps { def module: ModuleInstance - trait ReturnSite + case class StagedConcreteNum(tipe: ValueType, i: Rep[Num]) - trait StagedNum { - def tipe: ValueType - } - - trait StagedConcreteNum { - def tipe: ValueType = this match { - case I32C(_) => NumType(I32Type) - case I64C(_) => NumType(I64Type) - case F32C(_) => NumType(F32Type) - case F64C(_) => NumType(F64Type) - } - - def i: Rep[Num] - } - - case class I32C(i: Rep[Num]) extends StagedConcreteNum - case class I64C(i: Rep[Num]) extends StagedConcreteNum - case class F32C(i: Rep[Num]) extends StagedConcreteNum - case class F64C(i: Rep[Num]) extends StagedConcreteNum - - trait StagedSymbolicNum { - def tipe: ValueType = this match { - case I32S(_) => NumType(I32Type) - case I64S(_) => NumType(I64Type) - case F32S(_) => NumType(F32Type) - case F64S(_) => NumType(F64Type) - } - - def s: Rep[SymVal] - } - - case class I32S(s: Rep[SymVal]) extends StagedSymbolicNum - case class I64S(s: Rep[SymVal]) extends StagedSymbolicNum - case class F32S(s: Rep[SymVal]) extends StagedSymbolicNum - case class F64S(s: Rep[SymVal]) extends StagedSymbolicNum + case class StagedSymbolicNum(tipe: ValueType, s: Rep[SymVal]) def toStagedNum(num: Num): StagedConcreteNum = { num match { - case I32V(_) => I32C(num) - case I64V(_) => I64C(num) - case F32V(_) => F32C(num) - case F64V(_) => F64C(num) + case I32V(_) => StagedConcreteNum(NumType(I32Type), num) + case I64V(_) => StagedConcreteNum(NumType(I64Type), num) + case F32V(_) => StagedConcreteNum(NumType(F32Type), num) + case F64V(_) => StagedConcreteNum(NumType(F64Type), num) } } def toStagedSymbolicNum(num: Num): StagedSymbolicNum = { num match { - case I32V(_) => I32S(Concrete(num)) - case I64V(_) => I64S(Concrete(num)) - case F32V(_) => F32S(Concrete(num)) - case F64V(_) => F64S(Concrete(num)) + case I32V(_) => StagedSymbolicNum(NumType(I32Type), Concrete(num)) + case I64V(_) => StagedSymbolicNum(NumType(I64Type), Concrete(num)) + case F32V(_) => StagedSymbolicNum(NumType(F32Type), Concrete(num)) + case F64V(_) => StagedSymbolicNum(NumType(F64Type), Concrete(num)) } } @@ -115,24 +81,6 @@ trait StagedWasmEvaluator extends SAIOps { case NumType(F32Type) => 4 case NumType(F64Type) => 8 } - - def concreteTag: (Rep[Num]) => StagedConcreteNum = { - ty match { - case NumType(I32Type) => I32C - case NumType(I64Type) => I64C - case NumType(F32Type) => F32C - case NumType(F64Type) => F64C - } - } - - def symbolicTag: (Rep[SymVal]) => StagedSymbolicNum = { - ty match { - case NumType(I32Type) => I32S - case NumType(I64Type) => I64S - case NumType(F32Type) => F32S - case NumType(F64Type) => F64S - } - } } case class Context( @@ -225,7 +173,7 @@ trait StagedWasmEvaluator extends SAIOps { val id = Stack.popS(ty) val symVal = id.makeSymbolic(ty) val num = SymEnv.read(symVal.s) - Stack.pushC(ty.concreteTag(num)) + Stack.pushC(StagedConcreteNum(ty, num)) Stack.pushS(symVal) val newCtx = ctx.pop()._2.push(ty) eval(rest, kont, mkont, trail)(newCtx) @@ -295,8 +243,8 @@ trait StagedWasmEvaluator extends SAIOps { // For now, we assume that the result of memory.grow only depends on the execution path, // we can relax this by turning it return to a symbol value and mimic the memory.grow's result as input. val retSym = "Concrete".reflectCtrlWith[SymVal](retNum) - Stack.pushC(I32C(retNum)) - Stack.pushS(I32S(retSym)) + Stack.pushC(StagedConcreteNum(NumType(I32Type), retNum)) + Stack.pushS(StagedSymbolicNum(NumType(I32Type), retSym)) val newCtx2 = ctx.push(NumType(I32Type)) eval(rest, kont, mkont, trail)(newCtx2) case MemoryFill => ??? @@ -722,47 +670,25 @@ trait StagedWasmEvaluator extends SAIOps { "stack-init".reflectCtrlWith[Unit]() } - def popC(ty: ValueType): StagedConcreteNum = ty match { - case NumType(I32Type) => I32C("stack-pop".reflectCtrlWith[Num]()) - case NumType(I64Type) => I64C("stack-pop".reflectCtrlWith[Num]()) - case NumType(F32Type) => F32C("stack-pop".reflectCtrlWith[Num]()) - case NumType(F32Type) => F64C("stack-pop".reflectCtrlWith[Num]()) + def popC(ty: ValueType): StagedConcreteNum = { + StagedConcreteNum(ty, "stack-pop".reflectCtrlWith[Num]()) } - def popS(ty: ValueType): StagedSymbolicNum = ty match { - case NumType(I32Type) => I32S("sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(I64Type) => I64S("sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F32S("sym-stack-pop".reflectCtrlWith[SymVal]()) - case NumType(F64Type) => F64S("sym-stack-pop".reflectCtrlWith[SymVal]()) + def popS(ty: ValueType): StagedSymbolicNum = { + StagedSymbolicNum(ty, "sym-stack-pop".reflectCtrlWith[SymVal]()) } - def peekC(ty: ValueType): StagedConcreteNum = ty match { - case NumType(I32Type) => I32C("stack-peek".reflectCtrlWith[Num]()) - case NumType(I64Type) => I64C("stack-peek".reflectCtrlWith[Num]()) - case NumType(F32Type) => F32C("stack-peek".reflectCtrlWith[Num]()) - case NumType(F32Type) => F64C("stack-peek".reflectCtrlWith[Num]()) + def peekC(ty: ValueType): StagedConcreteNum = { + StagedConcreteNum(ty, "stack-peek".reflectCtrlWith[Num]()) } - def peekS(ty: ValueType): StagedSymbolicNum = ty match { - case NumType(I32Type) => I32S("sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(I64Type) => I64S("sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(F32Type) => F32S("sym-stack-peek".reflectCtrlWith[SymVal]()) - case NumType(F64Type) => F64S("sym-stack-peek".reflectCtrlWith[SymVal]()) + def peekS(ty: ValueType): StagedSymbolicNum = { + StagedSymbolicNum(ty, "sym-stack-peek".reflectCtrlWith[SymVal]()) } - def pushC(num: StagedConcreteNum) = num match { - case I32C(v) => "stack-push".reflectCtrlWith[Unit](v) - case I64C(v) => "stack-push".reflectCtrlWith[Unit](v) - case F32C(v) => "stack-push".reflectCtrlWith[Unit](v) - case F64C(v) => "stack-push".reflectCtrlWith[Unit](v) - } + def pushC(num: StagedConcreteNum) = "stack-push".reflectCtrlWith[Unit](num.i) - def pushS(num: StagedSymbolicNum) = num match { - case I32S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) - case I64S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) - case F32S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) - case F64S(s) => "sym-stack-push".reflectCtrlWith[Unit](s) - } + def pushS(num: StagedSymbolicNum) = "sym-stack-push".reflectCtrlWith[Unit](num.s) def takeC(types: List[ValueType]): List[StagedConcreteNum] = types match { case Nil => Nil @@ -792,39 +718,19 @@ trait StagedWasmEvaluator extends SAIOps { object Frames { def getC(i: Int)(implicit ctx: Context): StagedConcreteNum = { // val offset = ctx.frameTypes.take(i).map(_.size).sum - ctx.frameTypes(i) match { - case NumType(I32Type) => I32C("frame-get".reflectCtrlWith[Num](i)) - case NumType(I64Type) => I64C("frame-get".reflectCtrlWith[Num](i)) - case NumType(F32Type) => F32C("frame-get".reflectCtrlWith[Num](i)) - case NumType(F64Type) => F64C("frame-get".reflectCtrlWith[Num](i)) - } + StagedConcreteNum(ctx.frameTypes(i), "frame-get".reflectCtrlWith[Num](i)) } def getS(i: Int)(implicit ctx: Context): StagedSymbolicNum = { - ctx.frameTypes(i) match { - case NumType(I32Type) => I32S("sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(I64Type) => I64S("sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(F32Type) => F32S("sym-frame-get".reflectCtrlWith[SymVal](i)) - case NumType(F64Type) => F64S("sym-frame-get".reflectCtrlWith[SymVal](i)) - } + StagedSymbolicNum(ctx.frameTypes(i), "sym-frame-get".reflectCtrlWith[SymVal](i)) } def setC(i: Int, v: StagedConcreteNum): Rep[Unit] = { - v match { - case I32C(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case I64C(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case F32C(v) => "frame-set".reflectCtrlWith[Unit](i, v) - case F64C(v) => "frame-set".reflectCtrlWith[Unit](i, v) - } + "frame-set".reflectCtrlWith[Unit](i, v.i) } def setS(i: Int, s: StagedSymbolicNum): Rep[Unit] = { - s match { - case I32S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) - case I64S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) - case F32S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) - case F64S(s) => "sym-frame-set".reflectCtrlWith[Unit](i, s) - } + "sym-frame-set".reflectCtrlWith[Unit](i, s.s) } def pushFrameC(locals: List[ValueType]): Rep[Unit] = { @@ -867,11 +773,11 @@ trait StagedWasmEvaluator extends SAIOps { } def loadIntC(base: Rep[Int], offset: Int): StagedConcreteNum = { - I32C("I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset))) + StagedConcreteNum(NumType(I32Type), "I32V".reflectCtrlWith[Num]("memory-load-int".reflectCtrlWith[Int](base, offset))) } def loadIntS(base: Rep[Int], offset: Int): StagedSymbolicNum = { - I32S("sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) + StagedSymbolicNum(NumType(I32Type), "sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) } // Returns the previous memory size on success, or -1 if the memory cannot be grown. @@ -924,43 +830,23 @@ trait StagedWasmEvaluator extends SAIOps { } def getC(i: Int): StagedConcreteNum = { - module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => I32C("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(I64Type), _) => I64C("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(F32Type), _) => F32C("global-get".reflectCtrlWith[Num](i)) - case GlobalType(NumType(F64Type), _) => F64C("global-get".reflectCtrlWith[Num](i)) - } + StagedConcreteNum(module.globals(i).ty.ty, "global-get".reflectCtrlWith[Num](i)) } def getS(i: Int): StagedSymbolicNum = { - module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => I32S("sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(I64Type), _) => I64S("sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(F32Type), _) => F32S("sym-global-get".reflectCtrlWith[SymVal](i)) - case GlobalType(NumType(F64Type), _) => F64S("sym-global-get".reflectCtrlWith[SymVal](i)) - } + StagedSymbolicNum(module.globals(i).ty.ty, "sym-global-get".reflectCtrlWith[SymVal](i)) } def setC(i: Int, v: StagedConcreteNum): Rep[Unit] = { - module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) - case GlobalType(NumType(I64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) - case GlobalType(NumType(F32Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) - case GlobalType(NumType(F64Type), _) => "global-set".reflectCtrlWith[Unit](i, v.i) - } + "global-set".reflectCtrlWith[Unit](i, v.i) } def setS(i: Int, s: StagedSymbolicNum): Rep[Unit] = { - module.globals(i).ty match { - case GlobalType(NumType(I32Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) - case GlobalType(NumType(I64Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) - case GlobalType(NumType(F32Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) - case GlobalType(NumType(F64Type), _) => "sym-global-set".reflectCtrlWith[Unit](i, s.s) - } + "sym-global-set".reflectCtrlWith[Unit](i, s.s) } } - // Exploration tree, + // Exploration tree, object ExploreTree { def fillWithIfElse(s: Rep[SymVal], id: Int): Rep[Unit] = { "tree-fill-if-else".reflectCtrlWith[Unit](s, id) @@ -993,320 +879,414 @@ trait StagedWasmEvaluator extends SAIOps { // runtime Num type implicit class StagedConcreteNumOps(num: StagedConcreteNum) { - def makeSymbolic(ty: ValueType): StagedSymbolicNum = num match { - case I32C(x) => I32S("make-symbolic-concrete".reflectCtrlWith[SymVal](num.toInt)) + def makeSymbolic(ty: ValueType): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => + StagedSymbolicNum(NumType(I32Type), "make-symbolic-concrete".reflectCtrlWith[SymVal](num.toInt)) } def toInt: Rep[Int] = "num-to-int".reflectCtrlWith[Int](num.i) - def isZero(): StagedConcreteNum = num match { - case I32C(x_c) => I32C(Values.I32V("is-zero".reflectCtrlWith[Int](num.toInt))) + def isZero(): StagedConcreteNum = num.tipe match { + case NumType(I32Type) => + StagedConcreteNum(NumType(I32Type), Values.I32V("is-zero".reflectCtrlWith[Int](num.toInt))) } - def clz(): StagedConcreteNum = num match { - case I32C(x) => I32C("clz".reflectCtrlWith[Num](x)) - case I64C(x) => I64C("clz".reflectCtrlWith[Num](x)) + def clz(): StagedConcreteNum = num.tipe match { + case NumType(I32Type) => StagedConcreteNum(NumType(I32Type), "clz".reflectCtrlWith[Num](num.i)) + case NumType(I64Type) => StagedConcreteNum(NumType(I64Type), "clz".reflectCtrlWith[Num](num.i)) } - def ctz(): StagedConcreteNum = num match { - case I32C(x) => I32C("ctz".reflectCtrlWith[Num](x)) - case I64C(x) => I64C("ctz".reflectCtrlWith[Num](x)) + def ctz(): StagedConcreteNum = num.tipe match { + case NumType(I32Type) => StagedConcreteNum(NumType(I32Type), "ctz".reflectCtrlWith[Num](num.i)) + case NumType(I64Type) => StagedConcreteNum(NumType(I64Type), "ctz".reflectCtrlWith[Num](num.i)) } - def popcnt(): StagedConcreteNum = num match { - case I32C(x) => I32C("popcnt".reflectCtrlWith[Num](x)) - case I64C(x) => I64C("popcnt".reflectCtrlWith[Num](x)) + def popcnt(): StagedConcreteNum = num.tipe match { + case NumType(I32Type) => StagedConcreteNum(NumType(I32Type), "popcnt".reflectCtrlWith[Num](num.i)) + case NumType(I64Type) => StagedConcreteNum(NumType(I64Type), "popcnt".reflectCtrlWith[Num](num.i)) } - def +(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-add".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-add".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-add".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-add".reflectCtrlWith[Num](x, y)) - } + def +(rhs: StagedConcreteNum): StagedConcreteNum = (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) } - def -(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-sub".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-sub".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-sub".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-sub".reflectCtrlWith[Num](x, y)) - } + def -(rhs: StagedConcreteNum): StagedConcreteNum = (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) } def *(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-mul".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-mul".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-mul".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-mul".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) } } def /(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-div".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-div".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-div".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-div".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) } } def <<(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-shl".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-shl".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-shl".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-shl".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) } } def >>(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-shr".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-shr".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-shr".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-shr".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) } } def &(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("binary-and".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I64C("binary-and".reflectCtrlWith[Num](x, y)) - case (F32C(x), F32C(y)) => F32C("binary-and".reflectCtrlWith[Num](x, y)) - case (F64C(x), F64C(y)) => F64C("binary-and".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(F32Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(F64Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) } } def numEq(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-eq".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-eq".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) } } def numNe(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-ne".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-ne".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) } } def <(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-lt".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-lt".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) } } def ltu(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-ltu".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-ltu".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) } } def >(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-gt".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-gt".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) } } def gtu(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-gtu".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-gtu".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) } } def <=(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-le".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-le".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-le".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-le".reflectCtrlWith[Num](num.i, rhs.i)) } } def leu(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-leu".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-leu".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) } } def >=(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-ge".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-ge".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) } } def geu(rhs: StagedConcreteNum): StagedConcreteNum = { - (num, rhs) match { - case (I32C(x), I32C(y)) => I32C("relation-geu".reflectCtrlWith[Num](x, y)) - case (I64C(x), I64C(y)) => I32C("relation-geu".reflectCtrlWith[Num](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I32Type), "relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) } } } implicit class StagedSymbolicNumOps(num: StagedSymbolicNum) { - def makeSymbolic(ty: ValueType): StagedSymbolicNum = num match { - case I32S(x) => I32S("make-symbolic".reflectCtrlWith[SymVal](x)) + def makeSymbolic(ty: ValueType): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => StagedSymbolicNum(NumType(I32Type), "make-symbolic".reflectCtrlWith[SymVal](num.s)) case _ => throw new RuntimeException("Symbol index must be an i32") } - def isZero(): StagedSymbolicNum = num match { - case I32S(x) => I32S("sym-is-zero".reflectCtrlWith[SymVal](x)) + def isZero(): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => StagedSymbolicNum(NumType(I32Type), "sym-is-zero".reflectCtrlWith[SymVal](num.s)) } - def clz(): StagedSymbolicNum = num match { - case I32S(x) => I32S("sym-clz".reflectCtrlWith[SymVal](x)) - case I64S(x) => I64S("sym-clz".reflectCtrlWith[SymVal](x)) + def clz(): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => StagedSymbolicNum(NumType(I32Type), "sym-clz".reflectCtrlWith[SymVal](num.s)) + case NumType(I64Type) => StagedSymbolicNum(NumType(I64Type), "sym-clz".reflectCtrlWith[SymVal](num.s)) } - def ctz(): StagedSymbolicNum = num match { - case I32S(x) => I32S("sym-ctz".reflectCtrlWith[SymVal](x)) - case I64S(x) => I64S("sym-ctz".reflectCtrlWith[SymVal](x)) + def ctz(): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => StagedSymbolicNum(NumType(I32Type), "sym-ctz".reflectCtrlWith[SymVal](num.s)) + case NumType(I64Type) => StagedSymbolicNum(NumType(I64Type), "sym-ctz".reflectCtrlWith[SymVal](num.s)) } - def popcnt(): StagedSymbolicNum = num match { - case I32S(x) => I32S("sym-popcnt".reflectCtrlWith[SymVal](x)) - case I64S(x) => I64S("sym-popcnt".reflectCtrlWith[SymVal](x)) + def popcnt(): StagedSymbolicNum = num.tipe match { + case NumType(I32Type) => StagedSymbolicNum(NumType(I32Type), "sym-popcnt".reflectCtrlWith[SymVal](num.s)) + case NumType(I64Type) => StagedSymbolicNum(NumType(I64Type), "sym-popcnt".reflectCtrlWith[SymVal](num.s)) } def +(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-add".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-add".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-add".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-add".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-add".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def -(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-sub".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-sub".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-sub".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-sub".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-sub".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def *(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-mul".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-mul".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-mul".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-mul".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-mul".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def /(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-div".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def <<(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-shl".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-shl".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-shl".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-shl".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-shl".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def >>(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-shr".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-shr".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-shr".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-shr".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-shr".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def &(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I64S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) - case (F32S(x), F32S(y)) => F32S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) - case (F64S(x), F64S(y)) => F64S("sym-binary-and".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-and".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-and".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-and".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-and".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def numEq(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-eq".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-eq".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-eq".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-eq".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def numNe(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-ne".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-ne".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ne".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ne".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def <(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-lt".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-lt".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def ltu(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("relation-ltu".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("relation-ltu".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def >(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-gt".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-gt".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gt".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gt".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def gtu(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-gtu".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-gtu".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gtu".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gtu".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def <=(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-le".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-le".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def leu(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-leu".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-leu".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-leu".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-leu".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def >=(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-ge".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-ge".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) } } def geu(rhs: StagedSymbolicNum): StagedSymbolicNum = { - (num, rhs) match { - case (I32S(x), I32S(y)) => I32S("sym-relation-geu".reflectCtrlWith[SymVal](x, y)) - case (I64S(x), I64S(y)) => I32S("sym-relation-geu".reflectCtrlWith[SymVal](x, y)) + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-geu".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-geu".reflectCtrlWith[SymVal](num.s, rhs.s)) } } } From 5656536f4e659dec0d875422bf2eb7e966816752 Mon Sep 17 00:00:00 2001 From: ahuoguo Date: Wed, 10 Sep 2025 00:12:03 -0400 Subject: [PATCH 035/105] correct behavior for global --- benchmarks/wasm/global-sym.wat | 21 +++++++++++++++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 2 +- .../genwasym/TestStagedConcolicEval.scala | 2 ++ 3 files changed, 24 insertions(+), 1 deletion(-) create mode 100644 benchmarks/wasm/global-sym.wat diff --git a/benchmarks/wasm/global-sym.wat b/benchmarks/wasm/global-sym.wat new file mode 100644 index 000000000..54f558942 --- /dev/null +++ b/benchmarks/wasm/global-sym.wat @@ -0,0 +1,21 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32) (result i32))) + + (func (;0;) (type 2) (param i32) (result i32) + local.get 0 + global.set 0 + global.get 0 + ) + (func (;1;) (type 1) + i32.const 0 + i32.symbolic + ;; TODO Somehow this value is always 0? + call 0 + ) + (start 1) + (memory (;0;) 2) + (export "main" (func 1)) + (global (;0;) (mut i32) (i32.const 42)) +) \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index aee63cdad..2c41e2ebb 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -1408,7 +1408,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "global-get", List(i), _) => emit("Globals.get("); shallow(i); emit(")") case Node(_, "sym-global-get", List(i), _) => - emit("SymGlobal.get("); shallow(i); emit(")") + emit("SymGlobals.get("); shallow(i); emit(")") case Node(_, "global-set", List(i, value), _) => emit("Globals.set("); shallow(i); emit(", "); shallow(value); emit(")") case Node(_, "sym-global-set", List(i, s_value), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 303a3fe51..851ef55df 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -76,6 +76,8 @@ class TestStagedConcolicEval extends FunSuite { // TODO: Waiting more symbolic operators' implementations // test("loop - concrete") { testFileConcreteCpp("./benchmarks/wasm/loop.wat", None, expect=Some(List(10))) } test("even-odd - concrete") { testFileConcreteCpp("./benchmarks/wasm/even_odd.wat", None, expect=Some(List(1))) } + // Try global + test("global - concrete") { testFileConcreteCpp("./benchmarks/wasm/global-sym.wat", None) } // TODO: Waiting symbolic memory's implementations // test("load - concrete") { testFileConcreteCpp("./benchmarks/wasm/load.wat", None, expect=Some(List(1))) } // test("btree - concrete") { testFileConcreteCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat") } From 51544e8fd0366e9d22614c8d86f4dbc0f30773c9 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 22 Sep 2025 22:49:02 -0400 Subject: [PATCH 036/105] make log function returning std::monostate/Unit type --- headers/wasm/concrete_rt.hpp | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 179ef245e..77f7588ad 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -11,18 +11,20 @@ #include #include -void info() { +inline std::monostate info() { #ifdef DEBUG std::cout << std::endl; #endif + return std::monostate{}; } template -void info(const T &first, const Args &...args) { +std::monostate info(const T &first, const Args &...args) { #ifdef DEBUG std::cout << first << " "; info(args...); #endif + return std::monostate{}; } struct Num { From 4bdc93b1fde5d3a95c0c4e571fbac50df22bfefe Mon Sep 17 00:00:00 2001 From: Alex Bai Date: Wed, 24 Sep 2025 11:30:40 +0800 Subject: [PATCH 037/105] Symbolic memory (#91) * move Memory_t to symbolic * failing cases for load * correct behavior for load/store (concrete) * test offset * test concolic, currently failed * oops * symstack and stack should be consistent * added test for extract(currently failing * extract & concat * some fixes, make btree example runable * tweak --------- Co-authored-by: butterunderflow --- benchmarks/wasm/Makefile | 7 + benchmarks/wasm/load-offset.wat | 19 ++ benchmarks/wasm/load-overflow1.wat | 19 ++ benchmarks/wasm/load-overflow2.wat | 19 ++ benchmarks/wasm/load.wat | 2 +- benchmarks/wasm/mem-sym-extract.wat | 32 +++ benchmarks/wasm/mem-sym.wat | 32 +++ headers/wasm/concrete_rt.hpp | 40 +--- headers/wasm/smt_solver.hpp | 19 ++ headers/wasm/symbolic_rt.hpp | 216 ++++++++++++++++-- .../scala/wasm/StagedConcolicMiniWasm.scala | 32 ++- .../genwasym/TestStagedConcolicEval.scala | 18 +- 12 files changed, 390 insertions(+), 65 deletions(-) create mode 100644 benchmarks/wasm/Makefile create mode 100644 benchmarks/wasm/load-offset.wat create mode 100644 benchmarks/wasm/load-overflow1.wat create mode 100644 benchmarks/wasm/load-overflow2.wat create mode 100644 benchmarks/wasm/mem-sym-extract.wat create mode 100644 benchmarks/wasm/mem-sym.wat diff --git a/benchmarks/wasm/Makefile b/benchmarks/wasm/Makefile new file mode 100644 index 000000000..bad47a229 --- /dev/null +++ b/benchmarks/wasm/Makefile @@ -0,0 +1,7 @@ +.PHONY: clean + +clean: + find . -type f -name '*.cpp' -delete + find . -type f -name '*.cpp.exe' -delete + find . -type d -name '*.dSYM' -exec rm -rf {} + + find . -type f -name '*.dot' -delete diff --git a/benchmarks/wasm/load-offset.wat b/benchmarks/wasm/load-offset.wat new file mode 100644 index 000000000..1c42df1b5 --- /dev/null +++ b/benchmarks/wasm/load-offset.wat @@ -0,0 +1,19 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (func (;0;) (type 0) (result i32) + i32.const 0 + i32.const 256 + i32.store + i32.const 0 + i32.load offset=1 + ) + (func (;1;) (type 1) + call 0 + ;; should be 1 + ;; drop + ) + (start 1) + (memory (;0;) 2) + (export "main" (func 1)) +) \ No newline at end of file diff --git a/benchmarks/wasm/load-overflow1.wat b/benchmarks/wasm/load-overflow1.wat new file mode 100644 index 000000000..9f005ea18 --- /dev/null +++ b/benchmarks/wasm/load-overflow1.wat @@ -0,0 +1,19 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (func (;0;) (type 0) (result i32) + i32.const 0 + i32.const 256 + i32.store + i32.const 1 + i32.load + ) + (func (;1;) (type 1) + call 0 + ;; should be 1 + ;; drop + ) + (start 1) + (memory (;0;) 2) + (export "main" (func 1)) +) \ No newline at end of file diff --git a/benchmarks/wasm/load-overflow2.wat b/benchmarks/wasm/load-overflow2.wat new file mode 100644 index 000000000..86c1a5745 --- /dev/null +++ b/benchmarks/wasm/load-overflow2.wat @@ -0,0 +1,19 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (func (;0;) (type 0) (result i32) + i32.const 0 + i32.const 65536 + i32.store + i32.const 2 + i32.load + ) + (func (;1;) (type 1) + call 0 + ;; should be 1 + ;; drop + ) + (start 1) + (memory (;0;) 2) + (export "main" (func 1)) +) \ No newline at end of file diff --git a/benchmarks/wasm/load.wat b/benchmarks/wasm/load.wat index 916328aa5..6c43d79b2 100644 --- a/benchmarks/wasm/load.wat +++ b/benchmarks/wasm/load.wat @@ -10,7 +10,7 @@ ) (func (;1;) (type 1) call 0 - ;; should be 65536 + ;; should be 1 ;; drop ) (start 1) diff --git a/benchmarks/wasm/mem-sym-extract.wat b/benchmarks/wasm/mem-sym-extract.wat new file mode 100644 index 000000000..ca7e70ebf --- /dev/null +++ b/benchmarks/wasm/mem-sym-extract.wat @@ -0,0 +1,32 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (param i32))) + (import "console" "assert" (func (type 3))) + (func (;1;) (type 2) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; if x == 256 + i32.const 1 ;; return 1 + else + i32.const 0 + call 0 ;; assert false + i32.const 1 ;; to satisfy the type checker, this line will never be reached + end + ) + (func (;2;) (type 1) + i32.const 0 + i32.symbolic ;; call it x + call 1 + ) + (start 2) + (memory (;0;) 2) + (export "main" (func 1)) + (global (;0;) (mut i32) (i32.const 42)) +) \ No newline at end of file diff --git a/benchmarks/wasm/mem-sym.wat b/benchmarks/wasm/mem-sym.wat new file mode 100644 index 000000000..c70940088 --- /dev/null +++ b/benchmarks/wasm/mem-sym.wat @@ -0,0 +1,32 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (param i32))) + (import "console" "assert" (func (type 3))) + (func (;1;) (type 2) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.load + i32.const 25 + i32.eq + if (result i32) ;; if x == 25 + i32.const 1 ;; return 1 + else + i32.const 0 + call 0 ;; assert false + i32.const 1 ;; to satisfy the type checker, this line will never be reached + end + ) + (func (;2;) (type 1) + i32.const 0 + i32.symbolic ;; call it x + call 1 + ) + (start 2) + (memory (;0;) 2) + (export "main" (func 1)) + (global (;0;) (mut i32) (i32.const 42)) +) \ No newline at end of file diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 77f7588ad..5d9243c4b 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -76,6 +76,7 @@ class Stack_t { Num pop() { #ifdef DEBUG assert(count > 0 && "Stack underflow"); + printf("[Debug] poping from stack, size of concrete stack is: %d\n", count); #endif Num num = stack_ptr[count - 1]; count--; @@ -101,9 +102,13 @@ class Stack_t { if (size < 0) { throw std::out_of_range("Invalid size: " + std::to_string(size)); } + std::cout << "Shifting stack by offset " << offset << " and size " << size + << std::endl; + std::cout << "Current stack size: " << count << std::endl; #endif // shift last `size` of numbers forward of `offset` for (int32_t i = count - size; i < count; ++i) { + assert(i - offset >= 0); stack_ptr[i - offset] = stack_ptr[i]; } count -= offset; @@ -197,39 +202,4 @@ static std::monostate unreachable() { static int32_t pagesize = 65536; static int32_t page_count = 0; -struct Memory_t { - std::vector memory; - Memory_t(int32_t init_page_count) : memory(init_page_count * pagesize) {} - - int32_t loadInt(int32_t base, int32_t offset) { - return *reinterpret_cast(static_cast(memory.data()) + - base + offset); - } - - std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { - *reinterpret_cast(static_cast(memory.data()) + base + - offset) = value; - return std::monostate{}; - } - - // grow memory by delta bytes when bytes > 0. return -1 if failed, return old - // size when success - int32_t grow(int32_t delta) { - if (delta <= 0) { - return memory.size(); - } - - try { - memory.resize(memory.size() + delta * pagesize); - auto old_page_count = page_count; - page_count += delta; - return memory.size(); - } catch (const std::bad_alloc &e) { - return -1; - } - } -}; - -static Memory_t Memory(1); // 1 page memory - #endif // WASM_CONCRETE_RT_HPP \ No newline at end of file diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 504422f70..64952bcc0 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -71,6 +71,9 @@ inline z3::expr Solver::build_z3_expr(const SymVal &sym_val) { } else if (auto concrete = std::dynamic_pointer_cast(sym_val.symptr)) { return z3_ctx.bv_val(concrete->value.value, 32); + } else if (auto smallbv = + std::dynamic_pointer_cast(sym_val.symptr)) { + return z3_ctx.bv_val(smallbv->get_value(), smallbv->get_size()); } else if (auto binary = std::dynamic_pointer_cast(sym_val.symptr)) { auto bit_width = 32; @@ -119,7 +122,23 @@ inline z3::expr Solver::build_z3_expr(const SymVal &sym_val) { case DIV: { return left / right; } + case B_AND: { + return left & right; } + case CONCAT: { + return z3::concat(left, right); + } + default: + throw std::runtime_error("Operation not supported: " + + std::to_string(binary->op)); + } + } else if (auto extract = dynamic_cast(sym_val.symptr.get())) { + assert(extract); + int high = extract->high * 8 - 1; + int low = extract->low * 8 - 8; + auto s = build_z3_expr(extract->value); + auto res = s.extract(high, low); + return res; } throw std::runtime_error("Unsupported symbolic value type"); } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 137d071df..d7aa70ed4 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -6,6 +6,7 @@ #include "utils.hpp" #include #include +#include #include #include #include @@ -48,8 +49,34 @@ class SymConcrete : public Symbolic { SymConcrete(Num num) : value(num) {} }; +class SmallBV : public Symbolic { +public: + SmallBV(int size, int64_t value) : size(size), value(value) {} + int get_size() const { return size; } + int64_t get_value() const { return value; } + +private: + int size; + int64_t value; +}; + struct SymBinary; +enum Operation { + ADD, // Addition + SUB, // Subtraction + MUL, // Multiplication + DIV, // Division + EQ, // Equal + NEQ, // Not equal + LT, // Less than + LEQ, // Less than or equal + GT, // Greater than + GEQ, // Greater than or equal + B_AND, // Bitwise AND + CONCAT, // Byte-level concatenation +}; + struct SymVal { std::shared_ptr symptr; @@ -59,7 +86,7 @@ struct SymVal { // data structure operations SymVal makeSymbolic() const; - // arithmetic operations + // bitvector arithmetic operations SymVal is_zero() const; SymVal add(const SymVal &other) const; SymVal minus(const SymVal &other) const; @@ -68,12 +95,19 @@ struct SymVal { SymVal eq(const SymVal &other) const; SymVal neq(const SymVal &other) const; SymVal lt(const SymVal &other) const; - SymVal leq(const SymVal &other) const; + SymVal le(const SymVal &other) const; SymVal gt(const SymVal &other) const; - SymVal geq(const SymVal &other) const; + SymVal ge(const SymVal &other) const; SymVal negate() const; + SymVal bitwise_and(const SymVal &other) const; + SymVal concat(const SymVal &other) const; + SymVal extract(int high, int low) const; + // TODO: add bitwise operations, and use the underlying bitvector theory bool is_concrete() const; + +private: + static SymVal make_binary(Operation op, const SymVal &lhs, const SymVal &rhs); }; static SymVal make_symbolic(int index) { @@ -84,7 +118,17 @@ inline SymVal Concrete(Num num) { return SymVal(std::make_shared(num)); } -enum Operation { ADD, SUB, MUL, DIV, EQ, NEQ, LT, LEQ, GT, GEQ }; +// Extract is different from other operations, it only has one symbolic operand, +// the other two operands are constants +// Extract from value, both high and low are inclusive byte indexes +struct SymExtract : Symbolic { + SymVal value; + int high; + int low; + + SymExtract(SymVal value, int high, int low) + : value(value), high(high), low(low) {} +}; struct SymBinary : Symbolic { Operation op; @@ -96,47 +140,70 @@ struct SymBinary : Symbolic { }; inline SymVal SymVal::add(const SymVal &other) const { - return SymVal(std::make_shared(ADD, *this, other)); + return make_binary(ADD, *this, other); } inline SymVal SymVal::minus(const SymVal &other) const { - return SymVal(std::make_shared(SUB, *this, other)); + return make_binary(SUB, *this, other); } inline SymVal SymVal::mul(const SymVal &other) const { - return SymVal(std::make_shared(MUL, *this, other)); + return make_binary(MUL, *this, other); } inline SymVal SymVal::div(const SymVal &other) const { - return SymVal(std::make_shared(DIV, *this, other)); + return make_binary(DIV, *this, other); } inline SymVal SymVal::eq(const SymVal &other) const { - return SymVal(std::make_shared(EQ, *this, other)); + return make_binary(EQ, *this, other); } inline SymVal SymVal::neq(const SymVal &other) const { - return SymVal(std::make_shared(NEQ, *this, other)); + return make_binary(NEQ, *this, other); } + inline SymVal SymVal::lt(const SymVal &other) const { - return SymVal(std::make_shared(LT, *this, other)); + return make_binary(LT, *this, other); } -inline SymVal SymVal::leq(const SymVal &other) const { - return SymVal(std::make_shared(LEQ, *this, other)); + +inline SymVal SymVal::le(const SymVal &other) const { + return make_binary(LEQ, *this, other); } + inline SymVal SymVal::gt(const SymVal &other) const { - return SymVal(std::make_shared(GT, *this, other)); + return make_binary(GT, *this, other); } -inline SymVal SymVal::geq(const SymVal &other) const { - return SymVal(std::make_shared(GEQ, *this, other)); + +inline SymVal SymVal::ge(const SymVal &other) const { + return make_binary(GEQ, *this, other); } + inline SymVal SymVal::is_zero() const { - return SymVal(std::make_shared(EQ, *this, Concrete(I32V(0)))); + return make_binary(EQ, *this, Concrete(I32V(0))); } + inline SymVal SymVal::negate() const { - return SymVal(std::make_shared(EQ, *this, Concrete(I32V(0)))); + return make_binary(EQ, *this, Concrete(I32V(0))); } +inline SymVal SymVal::concat(const SymVal &other) const { + return make_binary(CONCAT, *this, other); +} + +inline SymVal SymVal::extract(int high, int low) const { + assert(high >= low && "Invalid extract range"); + return SymVal(std::make_shared(*this, high, low)); +} + +inline SymVal SymVal::bitwise_and(const SymVal &other) const { + return make_binary(B_AND, *this, other); +} +inline SymVal SymVal::make_binary(Operation op, const SymVal &lhs, + const SymVal &rhs) { + assert(lhs.symptr != nullptr && rhs.symptr != nullptr); + return SymVal(std::make_shared(op, lhs, rhs)); +} inline SymVal SymVal::makeSymbolic() const { auto concrete = dynamic_cast(symptr.get()); if (concrete) { @@ -178,6 +245,7 @@ class SymStack_t { std::monostate shift(int32_t offset, int32_t size) { auto n = stack.size(); for (size_t i = n - size; i < n; ++i) { + assert(i - offset >= 0); stack[i - offset] = stack[i]; } stack.resize(n - offset); @@ -723,6 +791,17 @@ static SymEnv_t SymEnv; static Num eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { if (auto concrete = dynamic_cast(sym.symptr.get())) { return concrete->value; + } else if (auto extract = dynamic_cast(sym.symptr.get())) { + auto value = eval_sym_expr(extract->value, sym_env); + int high = extract->high; + int low = extract->low; + assert(high >= low && "Invalid extract range"); + int size = high - low + 1; // size in bytes + int64_t mask = (1LL << (size * 8)) - 1; + int64_t extracted_value = (value.toInt() >> (low * 8)) & mask; + return Num(I64V(extracted_value)); + } else if (auto smallbv = dynamic_cast(sym.symptr.get())) { + return Num(I64V(smallbv->get_value())); } else if (auto operation = dynamic_cast(sym.symptr.get())) { // If it's a operation, we need to evaluate it auto lhs = eval_sym_expr(operation->lhs, sym_env); @@ -744,8 +823,18 @@ static Num eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { return lhs > rhs; case GEQ: return lhs >= rhs; + case NEQ: + return lhs != rhs; + case EQ: + return lhs == rhs; + case B_AND: + return Num(I64V(lhs.value & rhs.value)); + case CONCAT: + // we must know the size of lhs and rhs in bytes to support concat + throw std::runtime_error( + "Concatenation operation not supported in evaluation"); default: - throw std::runtime_error("Operation not supported: " + + throw std::runtime_error("Operation not supported in evaluation: " + std::to_string(operation->op)); } } else if (auto symbol = dynamic_cast(sym.symptr.get())) { @@ -798,4 +887,93 @@ inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, return cont(mcont); } +struct Memory_t { + // TODO: We assign a SymVal to each byte in memory + std::vector> memory; + + Memory_t(int32_t init_page_count) : memory(init_page_count * pagesize) {} + + int32_t loadInt(int32_t base, int32_t offset) { + // just load a 4-byte integer from memory of the vector + int32_t addr = base + offset; + assert(addr + 3 < memory.size()); + int32_t result = 0; + // Little-endian: lowest byte at lowest address + for (int i = 0; i < 4; ++i) { + result |= static_cast(memory[addr + i].first) << (8 * i); + } + return result; + } + + // TODO: when loading a symval, we need to concat 4 symbolic values + // This sounds terribly bad for SMT... + // Load a 4-byte symbolic value from memory + SymVal loadSym(int32_t base, int32_t offset) { + int32_t addr = base + offset; + assert(addr + 3 < memory.size()); + SymVal s0 = memory[addr].second; + if (s0.symptr == nullptr) { + s0 = SymVal(std::make_shared(8, 0)); + } + SymVal s1 = memory[addr + 1].second; + if (s1.symptr == nullptr) { + s1 = SymVal(std::make_shared(8, 0)); + } + SymVal s2 = memory[addr + 2].second; + if (s2.symptr == nullptr) { + s2 = SymVal(std::make_shared(8, 0)); + } + SymVal s3 = memory[addr + 3].second; + if (s3.symptr == nullptr) { + s3 = SymVal(std::make_shared(8, 0)); + } + return s0.concat(s1).concat(s2).concat(s3); + } + + // Store a 4-byte symbolic value to memory + std::monostate storeSym(int32_t base, int32_t offset, SymVal value) { + int32_t addr = base + offset; + // Extract 4 bytes from that symbol + SymVal s0 = value.extract(1, 1); + SymVal s1 = value.extract(2, 2); + SymVal s2 = value.extract(3, 3); + SymVal s3 = value.extract(4, 4); + memory[addr].second = s0; + memory[addr + 1].second = s1; + memory[addr + 2].second = s2; + memory[addr + 3].second = s3; + return std::monostate{}; + } + + std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { + int32_t addr = base + offset; + // Ensure we don't write out of bounds + assert(addr + 3 < memory.size()); + for (int i = 0; i < 4; ++i) { + memory[addr + i].first = static_cast((value >> (8 * i)) & 0xFF); + // Optionally, update memory[addr + i].second (SymVal) if needed + } + return std::monostate{}; + } + + // grow memory by delta bytes when bytes > 0. return -1 if failed, return old + // size when success + int32_t grow(int32_t delta) { + if (delta <= 0) { + return memory.size(); + } + + try { + memory.resize(memory.size() + delta * pagesize); + auto old_page_count = page_count; + page_count += delta; + return memory.size(); + } catch (const std::bad_alloc &e) { + return -1; + } + } +}; + +static Memory_t Memory(1); // 1 page memory + #endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 2c41e2ebb..5b5ae8de6 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -220,7 +220,7 @@ trait StagedWasmEvaluator extends SAIOps { val (ty2, newCtx2) = newCtx1.pop() val addr = Stack.popC(ty2) val symAddr = Stack.popS(ty2) - Memory.storeInt(addr.toInt, offset, value.toInt) + Memory.storeInt(addr.toInt, offset, (value.toInt, symValue)) eval(rest, kont, mkont, trail)(newCtx2) case Nop => eval(rest, kont, mkont, trail) case Load(LoadOp(align, offset, ty, None, None)) => @@ -245,7 +245,7 @@ trait StagedWasmEvaluator extends SAIOps { val retSym = "Concrete".reflectCtrlWith[SymVal](retNum) Stack.pushC(StagedConcreteNum(NumType(I32Type), retNum)) Stack.pushS(StagedSymbolicNum(NumType(I32Type), retSym)) - val newCtx2 = ctx.push(NumType(I32Type)) + val newCtx2 = newCtx.push(NumType(I32Type)) eval(rest, kont, mkont, trail)(newCtx2) case MemoryFill => ??? case Unreachable => unreachable() @@ -767,9 +767,11 @@ trait StagedWasmEvaluator extends SAIOps { } object Memory { - def storeInt(base: Rep[Int], offset: Int, value: Rep[Int]): Rep[Unit] = { - "memory-store-int".reflectCtrlWith[Unit](base, offset, value) - // todo: store symbolic value to memory via extract/concat operation + // TODO: why this is only one function, rather than `storeInC` and `storeInS`? + // TODO: what should the type of SymVal be? + def storeInt(base: Rep[Int], offset: Int, value: (Rep[Int], StagedSymbolicNum)): Rep[Unit] = { + "memory-store-int".reflectCtrlWith[Unit](base, offset, value._1) + "sym-store-int".reflectCtrlWith[Unit](base, offset, value._2.s) } def loadIntC(base: Rep[Int], offset: Int): StagedConcreteNum = { @@ -777,7 +779,7 @@ trait StagedWasmEvaluator extends SAIOps { } def loadIntS(base: Rep[Int], offset: Int): StagedSymbolicNum = { - StagedSymbolicNum(NumType(I32Type), "sym-load-int-todo".reflectCtrlWith[SymVal](base, offset)) + StagedSymbolicNum(NumType(I32Type), "sym-load-int".reflectCtrlWith[SymVal](base, offset)) } // Returns the previous memory size on success, or -1 if the memory cannot be grown. @@ -1405,6 +1407,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Memory.grow("); shallow(delta); emit(")") case Node(_, "stack-size", _, _) => emit("Stack.size()") + // Symbolic Memory + case Node(_, "sym-store-int", List(base, offset, s_value), _) => + emit("Memory.storeSym("); shallow(base); emit(", "); shallow(offset); emit(", "); shallow(s_value); emit(")") + case Node(_, "sym-load-int", List(base, offset), _) => + emit("Memory.loadSym("); shallow(base); emit(", "); shallow(offset); emit(")") + case Node(_, "sym-memory-grow", List(delta), _) => + emit("SymMemory.grow("); shallow(delta); emit(")") + // Globals case Node(_, "global-get", List(i), _) => emit("Globals.get("); shallow(i); emit(")") case Node(_, "sym-global-get", List(i), _) => @@ -1464,11 +1474,15 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".mul("); shallow(rhs); emit(")") case Node(_, "sym-binary-div", List(lhs, rhs), _) => shallow(lhs); emit(".div("); shallow(rhs); emit(")") + case Node(_, "sym-binary-and", List(lhs, rhs), _) => + shallow(lhs); emit(".bitwise_and("); shallow(rhs); emit(")") case Node(_, "sym-relation-le", List(lhs, rhs), _) => - shallow(lhs); emit(".leq("); shallow(rhs); emit(")") + shallow(lhs); emit(".le("); shallow(rhs); emit(")") case Node(_, "sym-relation-leu", List(lhs, rhs), _) => shallow(lhs); emit(".leu("); shallow(rhs); emit(")") - case Node(_, "sym-relation-ge", List(lhs, rhs), _) => + case Node(_, "sym-relation-lt", List(lhs, rhs), _) => + shallow(lhs); emit(".lt("); shallow(rhs); emit(")") + case Node(_, "sym-relation-ge", List(lhs, rhs), _) => shallow(lhs); emit(".ge("); shallow(rhs); emit(")") case Node(_, "sym-relation-geu", List(lhs, rhs), _) => shallow(lhs); emit(".geu("); shallow(rhs); emit(")") @@ -1476,6 +1490,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".eq("); shallow(rhs); emit(")") case Node(_, "sym-relation-ne", List(lhs, rhs), _) => shallow(lhs); emit(".neq("); shallow(rhs); emit(")") + case Node(_, "sym-relation-gt", List(lhs, rhs), _) => + shallow(lhs); emit(".gt("); shallow(rhs); emit(")") case Node(_, "num-to-int", List(num), _) => shallow(num); emit(".toInt()") case Node(_, "make-symbolic", List(num), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 851ef55df..03a5df091 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -66,6 +66,16 @@ class TestStagedConcolicEval extends FunSuite { testFileConcolicCpp("./benchmarks/wasm/staged/simple_global.wat", Some("real_main"), exitByCoverage=true) } + test("mem-sym-concolic") { + testFileConcolicCpp("./benchmarks/wasm/mem-sym.wat", None, exitByCoverage=true) + } + + test("mem-sym-extract-concolic") { + testFileConcolicCpp("./benchmarks/wasm/mem-sym-extract.wat", None, exitByCoverage=true) + } + test("btree-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat") } + + test("return-poly - concrete") { testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) } @@ -76,10 +86,14 @@ class TestStagedConcolicEval extends FunSuite { // TODO: Waiting more symbolic operators' implementations // test("loop - concrete") { testFileConcreteCpp("./benchmarks/wasm/loop.wat", None, expect=Some(List(10))) } test("even-odd - concrete") { testFileConcreteCpp("./benchmarks/wasm/even_odd.wat", None, expect=Some(List(1))) } - // Try global test("global - concrete") { testFileConcreteCpp("./benchmarks/wasm/global-sym.wat", None) } // TODO: Waiting symbolic memory's implementations - // test("load - concrete") { testFileConcreteCpp("./benchmarks/wasm/load.wat", None, expect=Some(List(1))) } + test("load - concrete") { testFileConcreteCpp("./benchmarks/wasm/load.wat", None, expect=Some(List(1))) } + test("load overflow 1 - concrete") { testFileConcreteCpp("./benchmarks/wasm/load-overflow1.wat", None, expect=Some(List(1))) } + test("load overflow 2 - concrete") { testFileConcreteCpp("./benchmarks/wasm/load-overflow2.wat", None, expect=Some(List(1))) } + + test("load offset - concrete") { testFileConcreteCpp("./benchmarks/wasm/load-offset.wat", None, expect=Some(List(1))) } + // test("btree - concrete") { testFileConcreteCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat") } test("fib - concrete") { testFileConcreteCpp("./benchmarks/wasm/fib.wat", None, expect=Some(List(144))) } test("tribonacci - concrete") { testFileConcreteCpp("./benchmarks/wasm/tribonacci.wat", None, expect=Some(List(504))) } From 74732ad5f4f47883a73bc57f9574c3f6724d2caa Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 24 Sep 2025 14:35:15 -0400 Subject: [PATCH 038/105] fix: high bits should be concat first --- benchmarks/wasm/mem-sym.wat | 15 +++++++++++++-- headers/wasm/symbolic_rt.hpp | 2 +- 2 files changed, 14 insertions(+), 3 deletions(-) diff --git a/benchmarks/wasm/mem-sym.wat b/benchmarks/wasm/mem-sym.wat index c70940088..45b9d1c3e 100644 --- a/benchmarks/wasm/mem-sym.wat +++ b/benchmarks/wasm/mem-sym.wat @@ -13,11 +13,22 @@ i32.const 25 i32.eq if (result i32) ;; if x == 25 - i32.const 1 ;; return 1 - else i32.const 0 call 0 ;; assert false i32.const 1 ;; to satisfy the type checker, this line will never be reached + else + i32.const 1 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; if x >> 8 == 1 + i32.const 0 + call 0 ;; assert false + i32.const 1 ;; to satisfy the type checker, this line will never be reached + else + i32.const 1 + end + i32.const 1 end ) (func (;2;) (type 1) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index d7aa70ed4..4c69f73b9 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -927,7 +927,7 @@ struct Memory_t { if (s3.symptr == nullptr) { s3 = SymVal(std::make_shared(8, 0)); } - return s0.concat(s1).concat(s2).concat(s3); + return s3.concat(s2).concat(s1).concat(s0); } // Store a 4-byte symbolic value to memory From e3f8488e4aa2841d7fedd71d6592e18d0b875626 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 28 Sep 2025 20:49:02 -0400 Subject: [PATCH 039/105] make btree example work with concolic execution --- benchmarks/wasm/btree/2o1u-unlabeled.wat | 5 +- headers/wasm/concolic_driver.hpp | 4 +- headers/wasm/symbolic_rt.hpp | 94 ++++++++++++------- .../genwasym/TestStagedConcolicEval.scala | 2 +- 4 files changed, 68 insertions(+), 37 deletions(-) diff --git a/benchmarks/wasm/btree/2o1u-unlabeled.wat b/benchmarks/wasm/btree/2o1u-unlabeled.wat index 096f10044..443bf5d4f 100644 --- a/benchmarks/wasm/btree/2o1u-unlabeled.wat +++ b/benchmarks/wasm/btree/2o1u-unlabeled.wat @@ -2626,9 +2626,12 @@ i32.and drop) (func (;7;) (type 4) - i32.const 3 i32.const 2 + i32.symbolic i32.const 1 + i32.symbolic + i32.const 0 + i32.symbolic call 6) (memory (;0;) 2) (export "main" (func 7)) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 81b5d5ad8..06b3459c1 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -8,6 +8,7 @@ #include #include #include +#include #include #include @@ -83,7 +84,8 @@ inline void ConcolicDriver::run() { GENSYM_INFO("Execution finished successfully with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); - } catch (...) { + } catch (std::runtime_error &e) { + std::cout << "Caught runtime error: " << e.what() << std::endl; ExploreTree.fillFailedNode(); GENSYM_INFO("Caught runtime error with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 4c69f73b9..96b2f039a 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -56,7 +56,7 @@ class SmallBV : public Symbolic { int64_t get_value() const { return value; } private: - int size; + int size; // in bits int64_t value; }; @@ -77,10 +77,13 @@ enum Operation { CONCAT, // Byte-level concatenation }; +static std::shared_ptr ZERO = + std::make_shared(I32V(0)); + struct SymVal { std::shared_ptr symptr; - SymVal() : symptr(nullptr) {} + SymVal() : symptr(ZERO) {} SymVal(std::shared_ptr symptr) : symptr(symptr) {} // data structure operations @@ -283,12 +286,13 @@ class SymFrames_t { SymVal get(int index) { // Get the symbolic value at the given frame index - return stack[stack.size() - 1 - index]; + auto res = stack[stack.size() - 1 - index]; + return res; } void set(int index, SymVal val) { // Set the symbolic value at the given index - // Not implemented yet + assert(val.symptr != nullptr); stack[stack.size() - 1 - index] = val; } @@ -786,61 +790,72 @@ class SymEnv_t { static SymEnv_t SymEnv; +struct EvalRes { + Num value; + int width; // in bits + EvalRes(Num value, int width) : value(value), width(width) {} +}; + // TODO: reduce the re-computation of the same symbolic expression, it's better // if it can be done by the smt solver -static Num eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { +static EvalRes eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { + assert(sym.symptr != nullptr && "Symbolic expression is null"); if (auto concrete = dynamic_cast(sym.symptr.get())) { - return concrete->value; + return EvalRes(concrete->value, 32); } else if (auto extract = dynamic_cast(sym.symptr.get())) { - auto value = eval_sym_expr(extract->value, sym_env); + auto res = eval_sym_expr(extract->value, sym_env); int high = extract->high; int low = extract->low; assert(high >= low && "Invalid extract range"); int size = high - low + 1; // size in bytes int64_t mask = (1LL << (size * 8)) - 1; - int64_t extracted_value = (value.toInt() >> (low * 8)) & mask; - return Num(I64V(extracted_value)); + int64_t extracted_value = (res.value.toInt() >> (low * 8)) & mask; + return EvalRes(Num(I64V(extracted_value)), size * 8); } else if (auto smallbv = dynamic_cast(sym.symptr.get())) { - return Num(I64V(smallbv->get_value())); + return EvalRes(Num(I64V(smallbv->get_value())), smallbv->get_size()); } else if (auto operation = dynamic_cast(sym.symptr.get())) { // If it's a operation, we need to evaluate it - auto lhs = eval_sym_expr(operation->lhs, sym_env); - auto rhs = eval_sym_expr(operation->rhs, sym_env); + auto lhs_res = eval_sym_expr(operation->lhs, sym_env); + auto rhs_res = eval_sym_expr(operation->rhs, sym_env); + auto lhs = lhs_res.value; + auto rhs = rhs_res.value; switch (operation->op) { case ADD: - return lhs + rhs; + return EvalRes(lhs + rhs, 32); case SUB: - return lhs - rhs; + return EvalRes(lhs - rhs, 32); case MUL: - return lhs * rhs; + return EvalRes(lhs * rhs, 32); case DIV: - return lhs / rhs; + return EvalRes(lhs / rhs, 32); case LT: - return lhs < rhs; + return EvalRes(lhs < rhs, 32); case LEQ: - return lhs <= rhs; + return EvalRes(lhs <= rhs, 32); case GT: - return lhs > rhs; + return EvalRes(lhs > rhs, 32); case GEQ: - return lhs >= rhs; + return EvalRes(lhs >= rhs, 32); case NEQ: - return lhs != rhs; + return EvalRes(lhs != rhs, 32); case EQ: - return lhs == rhs; + return EvalRes(lhs == rhs, 32); case B_AND: - return Num(I64V(lhs.value & rhs.value)); - case CONCAT: - // we must know the size of lhs and rhs in bytes to support concat - throw std::runtime_error( - "Concatenation operation not supported in evaluation"); + return EvalRes(Num(I64V(lhs.value & rhs.value)), 32); + case CONCAT: { + auto lhs_width = lhs_res.width; + auto rhs_width = rhs_res.width; + auto conc_value = (lhs.value << rhs_width) | (rhs.value); + auto new_width = lhs_width + rhs_width; + return EvalRes(Num(I64V(conc_value)), new_width); + } default: - throw std::runtime_error("Operation not supported in evaluation: " + - std::to_string(operation->op)); + assert(false && "Operation not supported in evaluation"); } } else if (auto symbol = dynamic_cast(sym.symptr.get())) { auto sym_id = symbol->get_id(); GENSYM_INFO("Reading symbol: " + std::to_string(sym_id)); - return sym_env.read(sym); + return EvalRes(sym_env.read(sym), 32); } throw std::runtime_error("Not supported symbolic expression"); } @@ -850,7 +865,8 @@ static void resume_conc_stack(const SymStack_t &sym_stack, Stack_t &stack, stack.resize(sym_stack.size()); for (size_t i = 0; i < sym_stack.size(); ++i) { auto sym = sym_stack[i]; - auto conc = eval_sym_expr(sym, sym_env); + auto res = eval_sym_expr(sym, sym_env); + auto conc = res.value; stack.set_from_front(i, conc); } } @@ -860,7 +876,9 @@ static void resume_conc_frames(const SymFrames_t &sym_frame, Frames_t &frames, frames.resize(sym_frame.size()); for (size_t i = 0; i < sym_frame.size(); ++i) { auto sym = sym_frame[i]; - auto conc = eval_sym_expr(sym, sym_env); + assert(sym.symptr != nullptr); + auto res = eval_sym_expr(sym, sym_env); + auto conc = res.value; frames.set_from_front(i, conc); } } @@ -896,7 +914,9 @@ struct Memory_t { int32_t loadInt(int32_t base, int32_t offset) { // just load a 4-byte integer from memory of the vector int32_t addr = base + offset; - assert(addr + 3 < memory.size()); + if (!(addr + 3 < memory.size())) { + throw std::runtime_error("Invalid memory access" + std::to_string(addr)); + } int32_t result = 0; // Little-endian: lowest byte at lowest address for (int i = 0; i < 4; ++i) { @@ -910,22 +930,28 @@ struct Memory_t { // Load a 4-byte symbolic value from memory SymVal loadSym(int32_t base, int32_t offset) { int32_t addr = base + offset; - assert(addr + 3 < memory.size()); + if (!(addr + 3 < memory.size())) { + throw std::runtime_error("Invalid memory access" + std::to_string(addr)); + } SymVal s0 = memory[addr].second; if (s0.symptr == nullptr) { s0 = SymVal(std::make_shared(8, 0)); + memory[addr].second = s0; } SymVal s1 = memory[addr + 1].second; if (s1.symptr == nullptr) { s1 = SymVal(std::make_shared(8, 0)); + memory[addr + 1].second = s1; } SymVal s2 = memory[addr + 2].second; if (s2.symptr == nullptr) { s2 = SymVal(std::make_shared(8, 0)); + memory[addr + 2].second = s2; } SymVal s3 = memory[addr + 3].second; if (s3.symptr == nullptr) { s3 = SymVal(std::make_shared(8, 0)); + memory[addr + 3].second = s3; } return s3.concat(s2).concat(s1).concat(s0); } diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 03a5df091..ada087ccf 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -73,7 +73,7 @@ class TestStagedConcolicEval extends FunSuite { test("mem-sym-extract-concolic") { testFileConcolicCpp("./benchmarks/wasm/mem-sym-extract.wat", None, exitByCoverage=true) } - test("btree-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat") } + test("btree-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat", exitByCoverage = true) } test("return-poly - concrete") { From 827f2b0bf2e4914bc64a6fd73b63b2e4969abf78 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Fri, 3 Oct 2025 13:20:55 -0400 Subject: [PATCH 040/105] preallocate pages for the memory --- headers/wasm/symbolic_rt.hpp | 40 +++++++++++++++++++++++++++++++----- 1 file changed, 35 insertions(+), 5 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 96b2f039a..975689287 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -4,6 +4,7 @@ #include "concrete_rt.hpp" #include "controls.hpp" #include "utils.hpp" +#include "wasm/profile.hpp" #include #include #include @@ -645,6 +646,14 @@ class ExploreTree_t { cursor = root.get(); } + void clear() { + GENSYM_INFO("Clearing the explore tree"); + root = std::make_unique(nullptr); + cursor = root.get(); + true_branch_cov_map.clear(); + false_branch_cov_map.clear(); + } + void set_cursor(NodeBox *new_cursor) { GENSYM_INFO("Setting cursor to a new node"); cursor = new_cursor; @@ -660,6 +669,7 @@ class ExploreTree_t { } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { + Profile.step(ProfileKind::CURSOR_MOVE); assert(cursor != nullptr); auto if_else_node = dynamic_cast(cursor->node.get()); assert( @@ -905,17 +915,30 @@ inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, return cont(mcont); } + +static const int PRE_ALLOC_PAGES = 20; + struct Memory_t { // TODO: We assign a SymVal to each byte in memory std::vector> memory; - - Memory_t(int32_t init_page_count) : memory(init_page_count * pagesize) {} + int page_count; + int allocated_pages; + + Memory_t(int32_t init_page_count) + : memory(PRE_ALLOC_PAGES * pagesize), page_count(init_page_count), + allocated_pages(PRE_ALLOC_PAGES) { + // warm up the memory with zero bytes + for (auto &byte : memory) { + byte.first = 0; + byte.second = SymVal(); + } + } int32_t loadInt(int32_t base, int32_t offset) { // just load a 4-byte integer from memory of the vector int32_t addr = base + offset; if (!(addr + 3 < memory.size())) { - throw std::runtime_error("Invalid memory access" + std::to_string(addr)); + throw std::runtime_error("Invalid memory access " + std::to_string(addr)); } int32_t result = 0; // Little-endian: lowest byte at lowest address @@ -931,7 +954,7 @@ struct Memory_t { SymVal loadSym(int32_t base, int32_t offset) { int32_t addr = base + offset; if (!(addr + 3 < memory.size())) { - throw std::runtime_error("Invalid memory access" + std::to_string(addr)); + throw std::runtime_error("Invalid memory access " + std::to_string(addr)); } SymVal s0 = memory[addr].second; if (s0.symptr == nullptr) { @@ -985,11 +1008,18 @@ struct Memory_t { // grow memory by delta bytes when bytes > 0. return -1 if failed, return old // size when success int32_t grow(int32_t delta) { + Profile.step(ProfileKind::MEM_GROW); if (delta <= 0) { - return memory.size(); + return page_count * pagesize; + } + + if (page_count + delta < allocated_pages) { + page_count += delta; + return page_count * pagesize; } try { + assert(false && "Use pre-allocated memory, should not reach here"); memory.resize(memory.size() + delta * pagesize); auto old_page_count = page_count; page_count += delta; From 75b6347802483974bf643633df56bd72d4e4fbea Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 4 Oct 2025 19:57:15 -0400 Subject: [PATCH 041/105] remove some unperformant code 1. dont intialize memory twice 2. dont allocate memory for unuse symbolic memory, because we need to copy them 3. profiling utilities --- headers/wasm.hpp | 5 +- headers/wasm/concolic_driver.hpp | 28 ++- headers/wasm/concrete_rt.hpp | 126 ++++++++-- headers/wasm/heap_mem_bookkeeper.hpp | 24 ++ headers/wasm/profile.hpp | 114 +++++++++ headers/wasm/symbolic_rt.hpp | 216 +++++++----------- headers/wasm/utils.hpp | 27 ++- .../scala/wasm/StagedConcolicMiniWasm.scala | 6 +- 8 files changed, 386 insertions(+), 160 deletions(-) create mode 100644 headers/wasm/heap_mem_bookkeeper.hpp create mode 100644 headers/wasm/profile.hpp diff --git a/headers/wasm.hpp b/headers/wasm.hpp index 36fe3849f..aa93e379f 100644 --- a/headers/wasm.hpp +++ b/headers/wasm.hpp @@ -1,8 +1,11 @@ #ifndef WASM_HEADERS #define WASM_HEADERS +#include "wasm/concolic_driver.hpp" #include "wasm/concrete_rt.hpp" +#include "wasm/controls.hpp" +#include "wasm/profile.hpp" #include "wasm/symbolic_rt.hpp" -#include "wasm/concolic_driver.hpp" #include "wasm/utils.hpp" + #endif \ No newline at end of file diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 06b3459c1..c9f0b8560 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -5,6 +5,9 @@ #include "smt_solver.hpp" #include "symbolic_rt.hpp" #include "utils.hpp" +#include "wasm/profile.hpp" +#include +#include #include #include #include @@ -35,6 +38,7 @@ class ConcolicDriver { void run(); private: + void main_exploration_loop(); Solver solver; std::function entrypoint; std::optional tree_file; @@ -46,13 +50,20 @@ class ManagedConcolicCleanup { public: ManagedConcolicCleanup(const ConcolicDriver &driver) : driver(driver) {} ~ManagedConcolicCleanup() { + // put any cleanup code that needs to be done after each execution here + + // Dump the explore tree if needed if (driver.tree_file.has_value()) ExploreTree.dump_graphviz(driver.tree_file.value()); + + // Clear the symbol bookkeeper + SymBookKeeper.clear(); } }; -inline void ConcolicDriver::run() { - ExploreTree.reset_cursor(); +static std::monostate reset_stacks(); + +inline void ConcolicDriver::main_exploration_loop() { while (true) { ManagedConcolicCleanup cleanup{*this}; @@ -79,6 +90,8 @@ inline void ConcolicDriver::run() { dynamic_cast(unexplored->node.get())) { snapshot_node->get_snapshot().resume_execution(SymEnv, unexplored); } else { + auto timer = ManagedTimer(); + reset_stacks(); entrypoint(); } @@ -97,7 +110,8 @@ inline void ConcolicDriver::run() { GENSYM_INFO("All branches covered, exiting..."); return; } else { - GENSYM_INFO("Found a bug, but not all branches covered, continuing..."); + GENSYM_INFO( + "Found a bug, but not all branches covered, continuing..."); } } } @@ -107,13 +121,19 @@ inline void ConcolicDriver::run() { } } +inline void ConcolicDriver::run() { + ExploreTree.reset_cursor(); + main_exploration_loop(); + Profile.print_summary(); +} + static std::monostate reset_stacks() { Stack.reset(); Frames.reset(); SymStack.reset(); SymFrames.reset(); initRand(); - Memory = Memory_t(1); + Memory.reset(); return std::monostate{}; } diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 5d9243c4b..cca614c6f 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -1,6 +1,7 @@ #ifndef WASM_CONCRETE_RT_HPP #define WASM_CONCRETE_RT_HPP +#include "wasm/profile.hpp" #include "wasm/utils.hpp" #include #include @@ -8,25 +9,10 @@ #include #include #include +#include #include #include -inline std::monostate info() { -#ifdef DEBUG - std::cout << std::endl; -#endif - return std::monostate{}; -} - -template -std::monostate info(const T &first, const Args &...args) { -#ifdef DEBUG - std::cout << first << " "; - info(args...); -#endif - return std::monostate{}; -} - struct Num { Num(int64_t value) : value(value) {} Num() : value(0) {} @@ -59,24 +45,34 @@ const int STACK_SIZE = 1024 * 64; class Stack_t { public: - Stack_t() : count(0), stack_ptr(new Num[STACK_SIZE]) {} + Stack_t() : count(0), stack_ptr(new Num[STACK_SIZE]) { + size_t page_size = (size_t)sysconf(_SC_PAGESIZE); + // pre touch the memory to avoid page faults during execution + for (int i = 0; i < STACK_SIZE; i += page_size) { + stack_ptr[i] = Num(0); + } + } std::monostate push(Num &&num) { + Profile.step(ProfileKind::PUSH); stack_ptr[count] = num; count++; return std::monostate{}; } std::monostate push(Num &num) { + Profile.step(ProfileKind::PUSH); stack_ptr[count] = num; count++; return std::monostate{}; } Num pop() { + Profile.step(ProfileKind::POP); #ifdef DEBUG assert(count > 0 && "Stack underflow"); - printf("[Debug] poping from stack, size of concrete stack is: %d\n", count); + printf("[Debug] popping from stack, size of concrete stack is: %d\n", + count); #endif Num num = stack_ptr[count - 1]; count--; @@ -84,6 +80,7 @@ class Stack_t { } Num peek() { + Profile.step(ProfileKind::PEEK); #ifdef DEBUG if (count == 0) { throw std::runtime_error("Stack underflow"); @@ -95,6 +92,7 @@ class Stack_t { int32_t size() { return count; } void shift(int32_t offset, int32_t size) { + Profile.step(ProfileKind::SHIFT); #ifdef DEBUG if (offset < 0) { throw std::out_of_range("Invalid offset: " + std::to_string(offset)); @@ -148,7 +146,13 @@ const int FRAME_SIZE = 1024; class Frames_t { public: - Frames_t() : count(0), stack_ptr(new Num[FRAME_SIZE]) {} + Frames_t() : count(0), stack_ptr(new Num[FRAME_SIZE]) { + size_t page_size = (size_t)sysconf(_SC_PAGESIZE); + // pre touch the memory to avoid page faults during execution + for (int i = 0; i < FRAME_SIZE; i += page_size) { + stack_ptr[i] = Num(0); + } + } std::monostate popFrame(std::int32_t size) { assert(size >= 0); @@ -157,11 +161,15 @@ class Frames_t { } Num get(std::int32_t index) { + Profile.step(ProfileKind::GET); auto ret = stack_ptr[count - 1 - index]; return ret; } - void set(std::int32_t index, Num num) { stack_ptr[count - 1 - index] = num; } + void set(std::int32_t index, Num num) { + Profile.step(ProfileKind::SET); + stack_ptr[count - 1 - index] = num; + } void pushFrame(std::int32_t size) { assert(size >= 0); @@ -199,7 +207,85 @@ static std::monostate unreachable() { throw std::runtime_error("Unreachable code reached"); } +static const int PRE_ALLOC_PAGES = 20; static int32_t pagesize = 65536; static int32_t page_count = 0; +struct Memory_t { + // TODO: We assign a SymVal to each byte in memory + std::vector memory; + int init_page_count; + int page_count; + int allocated_pages; + + Memory_t(int32_t init_page_count) + : memory(PRE_ALLOC_PAGES * pagesize), init_page_count(init_page_count), + page_count(init_page_count), allocated_pages(PRE_ALLOC_PAGES) {} + + int32_t loadInt(int32_t base, int32_t offset) { + // just load a 4-byte integer from memory of the vector + int32_t addr = base + offset; + if (!(addr + 3 < memory.size())) { + throw std::runtime_error("Invalid memory access " + std::to_string(addr)); + } + int32_t result = 0; + // Little-endian: lowest byte at lowest address + for (int i = 0; i < 4; ++i) { + result |= static_cast(memory[addr + i]) << (8 * i); + } + return result; + } + + std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { + int32_t addr = base + offset; + // Ensure we don't write out of bounds + assert(addr + 3 < memory.size()); + for (int i = 0; i < 4; ++i) { + memory[addr + i] = static_cast((value >> (8 * i)) & 0xFF); + // Optionally, update memory[addr + i].second (SymVal) if needed + } + return std::monostate{}; + } + + std::monostate store_byte(int32_t addr, uint8_t value) { + assert(addr < memory.size()); + memory[addr] = value; + return std::monostate{}; + } + + // grow memory by delta bytes when bytes > 0. return -1 if failed, return old + // size when success + int32_t grow(int32_t delta) { + Profile.step(ProfileKind::MEM_GROW); + if (delta <= 0) { + return page_count * pagesize; + } + + if (page_count + delta < allocated_pages) { + page_count += delta; + return page_count * pagesize; + } + + try { + assert(false && "Use pre-allocated memory, should not reach here"); + memory.resize(memory.size() + delta * pagesize); + auto old_page_count = page_count; + page_count += delta; + return memory.size(); + } catch (const std::bad_alloc &e) { + return -1; + } + } + + void reset() { + page_count = init_page_count; + allocated_pages = PRE_ALLOC_PAGES; + for (int i = 0; i < memory.size() && i < page_count * pagesize; ++i) { + memory[i] = 0; + } + } +}; + +static Memory_t Memory(1); // 1 page memory + #endif // WASM_CONCRETE_RT_HPP \ No newline at end of file diff --git a/headers/wasm/heap_mem_bookkeeper.hpp b/headers/wasm/heap_mem_bookkeeper.hpp new file mode 100644 index 000000000..c4cc7313f --- /dev/null +++ b/headers/wasm/heap_mem_bookkeeper.hpp @@ -0,0 +1,24 @@ +#ifndef HEAP_MEM_BOOKKEEPER_HPP +#define HEAP_MEM_BOOKKEEPER_HPP + +#include +#include + +// Todo: remove this later, this is just a workaround to make sure that the +// SymVals' memory will not be freed during the main execution. +// We can leave the SymVal's memory unmanaged if reference counting is not +// performant +template struct MemBookKeeper { + std::set> allocated; + + template + std::shared_ptr allocate(Args &&...args) { + auto ptr = std::make_shared(std::forward(args)...); + // allocated.insert(ptr); + return ptr; + } + + void clear() { allocated.clear(); } +}; + +#endif // HEAP_MEM_BOOKKEEPER_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp new file mode 100644 index 000000000..b112c932c --- /dev/null +++ b/headers/wasm/profile.hpp @@ -0,0 +1,114 @@ +#ifndef PROFILE_HPP +#define PROFILE_HPP + +#include "utils.hpp" +#include +#include +#include +#include + +enum class ProfileKind { + PUSH, + POP, + PEEK, + SHIFT, + SET, + GET, + BINARY, + TREE_FILL, + CURSOR_MOVE, + MEM_GROW, + SNAPSHOT_CREATE, + OperationCount // keep this as the last element, this is used to get the + // number of kinds of operations +}; + +class Profile_t { +public: + Profile_t() : step_count(0) {} + std::monostate step() { +#ifdef ENABLE_PROFILE + step_count++; +#endif + return std::monostate(); + } + std::monostate step(ProfileKind op) { +#ifdef ENABLE_PROFILE + op_count[static_cast(op)]++; +#endif + return std::monostate(); + } + void print_summary() { +#ifdef ENABLE_PROFILE + std::cout << "Profile Summary:" << std::endl; + std::cout << "Total PUSH operations: " + << op_count[static_cast(ProfileKind::PUSH)] + << std::endl; + std::cout << "Total POP operations: " + << op_count[static_cast(ProfileKind::POP)] + << std::endl; + std::cout << "Total PEEK operations: " + << op_count[static_cast(ProfileKind::PEEK)] + << std::endl; + std::cout << "Total SHIFT operations: " + << op_count[static_cast(ProfileKind::SHIFT)] + << std::endl; + std::cout << "Total SET operations: " + << op_count[static_cast(ProfileKind::SET)] + << std::endl; + std::cout << "Total GET operations: " + << op_count[static_cast(ProfileKind::GET)] + << std::endl; + std::cout << "Total BINARY operations: " + << op_count[static_cast(ProfileKind::BINARY)] + << std::endl; + std::cout << "Total TREE_FILL operations: " + << op_count[static_cast(ProfileKind::TREE_FILL)] + << std::endl; + std::cout << "Total CURSOR_MOVE operations: " + << op_count[static_cast(ProfileKind::CURSOR_MOVE)] + << std::endl; + std::cout << "Total other instructions executed: " << step_count + << std::endl; + std::cout << "Total MEM_GROW operations: " + << op_count[static_cast(ProfileKind::MEM_GROW)] + << std::endl; + std::cout + << "Total SNAPSHOT_CREATE operations: " + << op_count[static_cast(ProfileKind::SNAPSHOT_CREATE)] + << std::endl; + std::cout << "Total time for instruction execution (s): " + << std::setprecision(15) << execution_time << std::endl; +#endif + } + + // record the time spent in main instruction execution, in seconds + void add_instruction_time(double time) { +#ifdef ENABLE_PROFILE + execution_time += time; +#endif + } + +private: + int step_count; + std::array(ProfileKind::OperationCount)> + op_count; + double execution_time = 0.0; +}; + +static Profile_t Profile; + +class ManagedTimer { +public: + ManagedTimer() { start = std::chrono::high_resolution_clock::now(); } + ~ManagedTimer() { + auto end = std::chrono::high_resolution_clock::now(); + std::chrono::duration elapsed = end - start; + Profile.add_instruction_time(elapsed.count()); + } + +private: + std::chrono::high_resolution_clock::time_point start; +}; + +#endif // PROFILE_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 975689287..338afb774 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -3,8 +3,9 @@ #include "concrete_rt.hpp" #include "controls.hpp" +#include "heap_mem_bookkeeper.hpp" +#include "profile.hpp" #include "utils.hpp" -#include "wasm/profile.hpp" #include #include #include @@ -16,6 +17,7 @@ #include #include #include +#include #include #include @@ -60,7 +62,6 @@ class SmallBV : public Symbolic { int size; // in bits int64_t value; }; - struct SymBinary; enum Operation { @@ -77,9 +78,12 @@ enum Operation { B_AND, // Bitwise AND CONCAT, // Byte-level concatenation }; +static MemBookKeeper SymBookKeeper; static std::shared_ptr ZERO = - std::make_shared(I32V(0)); + SymBookKeeper.allocate(I32V(0)); +static std::shared_ptr ZeroByte = + SymBookKeeper.allocate(8, 0); struct SymVal { std::shared_ptr symptr; @@ -115,11 +119,11 @@ struct SymVal { }; static SymVal make_symbolic(int index) { - return SymVal(std::make_shared(index)); + return SymVal(SymBookKeeper.allocate(index)); } inline SymVal Concrete(Num num) { - return SymVal(std::make_shared(num)); + return SymVal(SymBookKeeper.allocate(num)); } // Extract is different from other operations, it only has one symbolic operand, @@ -197,7 +201,7 @@ inline SymVal SymVal::concat(const SymVal &other) const { inline SymVal SymVal::extract(int high, int low) const { assert(high >= low && "Invalid extract range"); - return SymVal(std::make_shared(*this, high, low)); + return SymVal(SymBookKeeper.allocate(*this, high, low)); } inline SymVal SymVal::bitwise_and(const SymVal &other) const { @@ -206,13 +210,13 @@ inline SymVal SymVal::bitwise_and(const SymVal &other) const { inline SymVal SymVal::make_binary(Operation op, const SymVal &lhs, const SymVal &rhs) { assert(lhs.symptr != nullptr && rhs.symptr != nullptr); - return SymVal(std::make_shared(op, lhs, rhs)); + return SymVal(SymBookKeeper.allocate(op, lhs, rhs)); } inline SymVal SymVal::makeSymbolic() const { auto concrete = dynamic_cast(symptr.get()); if (concrete) { // If the symbolic value is a concrete value, use it to create a symbol - return SymVal(std::make_shared(concrete->value.toInt())); + return SymVal(SymBookKeeper.allocate(concrete->value.toInt())); } else { throw std::runtime_error( "Cannot make symbolic a non-concrete symbolic value"); @@ -315,6 +319,55 @@ class SymFrames_t { struct NodeBox; struct SymEnv_t; +class SymMemory_t { +public: + std::unordered_map memory; + + SymVal loadSymByte(int32_t addr) { + // if the address is not in the memory, it must be a zero-initialized memory + auto it = memory.find(addr); + SymVal s = (it != memory.end()) + ? it->second + : SymVal(SymBookKeeper.allocate(8, 0)); + return s; + } + + SymVal loadSym(int32_t base, int32_t offset) { + // calculate the real address + int32_t addr = base + offset; + auto it = memory.find(addr); + SymVal s0 = (it != memory.end()) ? it->second : SymVal(ZeroByte); + it = memory.find(addr + 1); + SymVal s1 = (it != memory.end()) ? it->second : SymVal(ZeroByte); + it = memory.find(addr + 2); + SymVal s2 = (it != memory.end()) ? it->second : SymVal(ZeroByte); + it = memory.find(addr + 3); + SymVal s3 = (it != memory.end()) ? it->second : SymVal(ZeroByte); + + return s3.concat(s2).concat(s1).concat(s0); + } + + // when loading a symval, we need to concat 4 symbolic values + // This sounds terribly bad for SMT... + // Load a 4-byte symbolic value from memory + // Store a 4-byte symbolic value to memory + std::monostate storeSym(int32_t base, int32_t offset, SymVal value) { + int32_t addr = base + offset; + // Extract 4 bytes from that symbol + SymVal s0 = value.extract(1, 1); + SymVal s1 = value.extract(2, 2); + SymVal s2 = value.extract(3, 3); + SymVal s3 = value.extract(4, 4); + memory[addr] = s0; + memory[addr + 1] = s1; + memory[addr + 2] = s2; + memory[addr + 3] = s3; + return std::monostate{}; + } +}; + +static SymMemory_t SymMemory; + // A snapshot of the symbolic state and execution context (control) class Snapshot_t { public: @@ -322,12 +375,14 @@ class Snapshot_t { SymStack_t get_stack() const { return stack; } SymFrames_t get_frames() const { return frames; } + SymMemory_t get_memory() const { return memory; } std::monostate resume_execution(SymEnv_t &sym_env, NodeBox *node) const; private: SymStack_t stack; SymFrames_t frames; + SymMemory_t memory; // The continuation at the snapshot point Cont_t cont; MCont_t mcont; @@ -629,7 +684,9 @@ inline std::vector NodeBox::collect_path_conds() { } inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont) - : stack(SymStack), frames(SymFrames), cont(cont), mcont(mcont) { + : stack(SymStack), frames(SymFrames), memory(SymMemory), cont(cont), + mcont(mcont) { + Profile.step(ProfileKind::SNAPSHOT_CREATE); #ifdef DEBUG std::cout << "Creating snapshot of size " << stack.size() << std::endl; #endif @@ -893,11 +950,28 @@ static void resume_conc_frames(const SymFrames_t &sym_frame, Frames_t &frames, } } +static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, + SymEnv_t &sym_env) { + memory.reset(); + for (const auto &pair : sym_memory.memory) { + int32_t addr = pair.first; + SymVal sym = pair.second; + assert(sym.symptr != nullptr); + auto res = eval_sym_expr(sym, sym_env); + auto conc = res.value; + assert(res.width == 8 && "Memory should only store bytes"); + memory.store_byte(addr, conc.value & 0xFF); + } +} + static void resume_conc_states(const SymStack_t &sym_stack, - const SymFrames_t &sym_frame, Stack_t &stack, - Frames_t &frames, SymEnv_t &sym_env) { + const SymFrames_t &sym_frame, + const SymMemory_t &sym_memory, Stack_t &stack, + Frames_t &frames, Memory_t &memory, + SymEnv_t &sym_env) { resume_conc_stack(sym_stack, stack, sym_env); resume_conc_frames(sym_frame, frames, sym_env); + resume_conc_memory(sym_memory, memory, sym_env); } inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, @@ -909,127 +983,11 @@ inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, GENSYM_INFO("Reusing symbolic state from snapshot"); SymStack = stack; SymFrames = frames; + SymMemory = memory; // Restore the concrete states from the symbolic states - resume_conc_states(stack, frames, Stack, Frames, sym_env); + resume_conc_states(stack, frames, memory, Stack, Frames, Memory, sym_env); // Resume execution from the continuation return cont(mcont); } - -static const int PRE_ALLOC_PAGES = 20; - -struct Memory_t { - // TODO: We assign a SymVal to each byte in memory - std::vector> memory; - int page_count; - int allocated_pages; - - Memory_t(int32_t init_page_count) - : memory(PRE_ALLOC_PAGES * pagesize), page_count(init_page_count), - allocated_pages(PRE_ALLOC_PAGES) { - // warm up the memory with zero bytes - for (auto &byte : memory) { - byte.first = 0; - byte.second = SymVal(); - } - } - - int32_t loadInt(int32_t base, int32_t offset) { - // just load a 4-byte integer from memory of the vector - int32_t addr = base + offset; - if (!(addr + 3 < memory.size())) { - throw std::runtime_error("Invalid memory access " + std::to_string(addr)); - } - int32_t result = 0; - // Little-endian: lowest byte at lowest address - for (int i = 0; i < 4; ++i) { - result |= static_cast(memory[addr + i].first) << (8 * i); - } - return result; - } - - // TODO: when loading a symval, we need to concat 4 symbolic values - // This sounds terribly bad for SMT... - // Load a 4-byte symbolic value from memory - SymVal loadSym(int32_t base, int32_t offset) { - int32_t addr = base + offset; - if (!(addr + 3 < memory.size())) { - throw std::runtime_error("Invalid memory access " + std::to_string(addr)); - } - SymVal s0 = memory[addr].second; - if (s0.symptr == nullptr) { - s0 = SymVal(std::make_shared(8, 0)); - memory[addr].second = s0; - } - SymVal s1 = memory[addr + 1].second; - if (s1.symptr == nullptr) { - s1 = SymVal(std::make_shared(8, 0)); - memory[addr + 1].second = s1; - } - SymVal s2 = memory[addr + 2].second; - if (s2.symptr == nullptr) { - s2 = SymVal(std::make_shared(8, 0)); - memory[addr + 2].second = s2; - } - SymVal s3 = memory[addr + 3].second; - if (s3.symptr == nullptr) { - s3 = SymVal(std::make_shared(8, 0)); - memory[addr + 3].second = s3; - } - return s3.concat(s2).concat(s1).concat(s0); - } - - // Store a 4-byte symbolic value to memory - std::monostate storeSym(int32_t base, int32_t offset, SymVal value) { - int32_t addr = base + offset; - // Extract 4 bytes from that symbol - SymVal s0 = value.extract(1, 1); - SymVal s1 = value.extract(2, 2); - SymVal s2 = value.extract(3, 3); - SymVal s3 = value.extract(4, 4); - memory[addr].second = s0; - memory[addr + 1].second = s1; - memory[addr + 2].second = s2; - memory[addr + 3].second = s3; - return std::monostate{}; - } - - std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { - int32_t addr = base + offset; - // Ensure we don't write out of bounds - assert(addr + 3 < memory.size()); - for (int i = 0; i < 4; ++i) { - memory[addr + i].first = static_cast((value >> (8 * i)) & 0xFF); - // Optionally, update memory[addr + i].second (SymVal) if needed - } - return std::monostate{}; - } - - // grow memory by delta bytes when bytes > 0. return -1 if failed, return old - // size when success - int32_t grow(int32_t delta) { - Profile.step(ProfileKind::MEM_GROW); - if (delta <= 0) { - return page_count * pagesize; - } - - if (page_count + delta < allocated_pages) { - page_count += delta; - return page_count * pagesize; - } - - try { - assert(false && "Use pre-allocated memory, should not reach here"); - memory.resize(memory.size() + delta * pagesize); - auto old_page_count = page_count; - page_count += delta; - return memory.size(); - } catch (const std::bad_alloc &e) { - return -1; - } - } -}; - -static Memory_t Memory(1); // 1 page memory - #endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file diff --git a/headers/wasm/utils.hpp b/headers/wasm/utils.hpp index f814858d3..8b7b04711 100644 --- a/headers/wasm/utils.hpp +++ b/headers/wasm/utils.hpp @@ -1,5 +1,7 @@ #ifndef UTILS_HPP #define UTILS_HPP +#include +#include #ifndef GENSYM_ASSERT #define GENSYM_ASSERT(condition) \ @@ -39,15 +41,34 @@ #if __cplusplus < 202002L #include -inline bool starts_with(const std::string& str, const std::string& prefix) { +inline bool starts_with(const std::string &str, const std::string &prefix) { return str.size() >= prefix.size() && - std::equal(prefix.begin(), prefix.end(), str.begin()); + std::equal(prefix.begin(), prefix.end(), str.begin()); } #else #include -inline bool starts_with(const std::string& str, const std::string& prefix) { +inline bool starts_with(const std::string &str, const std::string &prefix) { return str.starts_with(prefix); } #endif +inline std::monostate info() { +#ifdef DEBUG + std::cout << std::endl; +#endif + return std::monostate{}; +} + +template +std::monostate info(const T &first, const Args &...args) { +#ifdef DEBUG + std::cout << first << " "; + info(args...); +#endif + return std::monostate{}; +} + +inline std::monostate get_unit() { return std::monostate{}; } +inline std::monostate get_unit(std::monostate x) { return std::monostate{}; } + #endif // UTILS_HPP \ No newline at end of file diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 5b5ae8de6..86d86a8a7 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -626,7 +626,7 @@ trait StagedWasmEvaluator extends SAIOps { } } val (instrs, locals) = (funBody.body, funBody.locals) - resetStacks() + // resetStacks() // Don't manually reset the global states (like stack), manage them in the driver initGlobals(module.globals) Frames.pushFrameC(locals) Frames.pushFrameS(locals) @@ -1409,9 +1409,9 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.size()") // Symbolic Memory case Node(_, "sym-store-int", List(base, offset, s_value), _) => - emit("Memory.storeSym("); shallow(base); emit(", "); shallow(offset); emit(", "); shallow(s_value); emit(")") + emit("SymMemory.storeSym("); shallow(base); emit(", "); shallow(offset); emit(", "); shallow(s_value); emit(")") case Node(_, "sym-load-int", List(base, offset), _) => - emit("Memory.loadSym("); shallow(base); emit(", "); shallow(offset); emit(")") + emit("SymMemory.loadSym("); shallow(base); emit(", "); shallow(offset); emit(")") case Node(_, "sym-memory-grow", List(delta), _) => emit("SymMemory.grow("); shallow(delta); emit(")") // Globals From 8a40d30b4a5d3c6b92b7ed712deba4567d74baea Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 4 Oct 2025 21:51:43 -0400 Subject: [PATCH 042/105] work list algorithm for exploration --- headers/wasm/concolic_driver.hpp | 39 ++++++++++++++++++++++++-------- headers/wasm/symbolic_rt.hpp | 36 +++++++++++++++++------------ 2 files changed, 52 insertions(+), 23 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index c9f0b8560..e49a99e83 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -42,6 +42,7 @@ class ConcolicDriver { Solver solver; std::function entrypoint; std::optional tree_file; + std::vector work_list; }; class ManagedConcolicCleanup { @@ -64,19 +65,39 @@ class ManagedConcolicCleanup { static std::monostate reset_stacks(); inline void ConcolicDriver::main_exploration_loop() { - while (true) { + + // Register a collector to ExploreTree to add new nodes to work_list + ExploreTree.register_new_node_collector( + [&](NodeBox *new_node) { work_list.push_back(new_node); }); + + std::set visited; + + assert(ExploreTree.get_root()->isUnexplored() && + "Before main loop, root should be unexplored!"); + work_list.push_back(ExploreTree.get_root()); + + while (!work_list.empty()) { ManagedConcolicCleanup cleanup{*this}; + // Pick an unexplored node from the work list + auto node = work_list.back(); + work_list.pop_back(); - auto unexplored = ExploreTree.pick_unexplored(); - if (!unexplored) { - GENSYM_INFO("No unexplored nodes found, exiting..."); - return; + if (visited.find(node) != visited.end()) { + continue; + } else { + visited.insert(node); } - auto cond = unexplored->collect_path_conds(); + + if (!node->isUnexplored()) { + // if it's not unexplored anymore, skip it + continue; + } + + auto cond = node->collect_path_conds(); auto result = solver.solve(cond); if (!result.has_value()) { GENSYM_INFO("Found an unreachable path, marking it as unreachable..."); - unexplored->fillUnreachableNode(); + node->fillUnreachableNode(); continue; } auto new_env = result.value(); @@ -87,8 +108,8 @@ inline void ConcolicDriver::main_exploration_loop() { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); if (auto snapshot_node = - dynamic_cast(unexplored->node.get())) { - snapshot_node->get_snapshot().resume_execution(SymEnv, unexplored); + dynamic_cast(node->node.get())) { + snapshot_node->get_snapshot().resume_execution(SymEnv, node); } else { auto timer = ManagedTimer(); reset_stacks(); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 338afb774..1cc3fb2d8 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -420,7 +420,7 @@ struct NodeBox { std::unique_ptr node; NodeBox *parent; - std::monostate fillIfElseNode(SymVal cond, int id); + bool fillIfElseNode(SymVal cond, int id); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -610,15 +610,16 @@ inline NodeBox::NodeBox(NodeBox *parent) /* TODO: avoid allocation of unexplored node */ parent(parent) {} -inline std::monostate NodeBox::fillIfElseNode(SymVal cond, int id) { +inline bool NodeBox::fillIfElseNode(SymVal cond, int id) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (this->isUnexplored()) { node = std::make_unique(cond, this, id); + return true; } assert( dynamic_cast(node.get()) != nullptr && "Current node is not an Unexplored nor an IfElseNode, cannot fill it!"); - return std::monostate(); + return false; } inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { @@ -722,7 +723,12 @@ class ExploreTree_t { std::monostate fillFailedNode() { return cursor->fillFailedNode(); } std::monostate fillIfElseNode(SymVal cond, int id) { - return cursor->fillIfElseNode(cond, id); + if (cursor->fillIfElseNode(cond, id)) { + auto if_else_node = dynamic_cast(cursor->node.get()); + register_new_node(if_else_node->true_branch.get()); + register_new_node(if_else_node->false_branch.get()); + } + return std::monostate(); } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { @@ -764,16 +770,6 @@ class ExploreTree_t { return std::monostate(); } - std::optional> get_unexplored_conditions() { - // Get all unexplored conditions in the tree - std::vector result; - auto box = pick_unexplored(); - if (!box) { - return std::nullopt; - } - return box->collect_path_conds(); - } - NodeBox *pick_unexplored() { // Pick an unexplored node from the tree // For now, we just iterate through the tree and return the first unexplored @@ -793,6 +789,12 @@ class ExploreTree_t { return true; } + NodeBox *get_root() const { return root.get(); } + + void register_new_node_collector(std::function func) { + new_node_collectors.push_back(func); + } + private: NodeBox *pick_unexplored_of(NodeBox *node) { if (node->isUnexplored()) { @@ -808,8 +810,14 @@ class ExploreTree_t { } return nullptr; // No unexplored node found } + void register_new_node(NodeBox *node) { + for (auto &func : new_node_collectors) { + func(node); + } + } std::unique_ptr root; NodeBox *cursor; + std::vector> new_node_collectors; }; static ExploreTree_t ExploreTree; From 568928c53494ac69fa6e92836f086e8d7df4c9c8 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 5 Oct 2025 12:20:09 -0400 Subject: [PATCH 043/105] config header; fix extract evaluation; capture by value in lambda --- headers/wasm/concolic_driver.hpp | 26 ++---- headers/wasm/concrete_rt.hpp | 47 +++++++--- headers/wasm/config.hpp | 36 +++++++ headers/wasm/profile.hpp | 93 +++++++++---------- headers/wasm/symbolic_rt.hpp | 72 +++++++------- .../scala/wasm/StagedConcolicMiniWasm.scala | 15 +-- 6 files changed, 166 insertions(+), 123 deletions(-) create mode 100644 headers/wasm/config.hpp diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index e49a99e83..37ef4004c 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -2,10 +2,11 @@ #define CONCOLIC_DRIVER_HPP #include "concrete_rt.hpp" +#include "config.hpp" +#include "profile.hpp" #include "smt_solver.hpp" #include "symbolic_rt.hpp" #include "utils.hpp" -#include "wasm/profile.hpp" #include #include #include @@ -15,16 +16,6 @@ #include #include -enum class ExploreMode { EarlyExit, ExitByCoverage }; - -#ifdef EARLY_EXIT -static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; -#elif defined(BY_COVERAGE) -static const ExploreMode EXPLORE_MODE = ExploreMode::ExitByCoverage; -#else -static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; -#endif - class ConcolicDriver { friend class ManagedConcolicCleanup; @@ -107,12 +98,14 @@ inline void ConcolicDriver::main_exploration_loop() { try { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); - if (auto snapshot_node = - dynamic_cast(node->node.get())) { + if (auto snapshot_node = dynamic_cast(node->node.get())) { + assert(REUSE_SNAPSHOT); + auto timer = ManagedTimer(); snapshot_node->get_snapshot().resume_execution(SymEnv, node); } else { auto timer = ManagedTimer(); reset_stacks(); + ExploreTree.reset_cursor(); entrypoint(); } @@ -134,6 +127,7 @@ inline void ConcolicDriver::main_exploration_loop() { GENSYM_INFO( "Found a bug, but not all branches covered, continuing..."); } + std::cout << e.what() << std::endl; } } #if defined(RUN_ONCE) @@ -143,18 +137,18 @@ inline void ConcolicDriver::main_exploration_loop() { } inline void ConcolicDriver::run() { - ExploreTree.reset_cursor(); main_exploration_loop(); Profile.print_summary(); } static std::monostate reset_stacks() { Stack.reset(); - Frames.reset(); SymStack.reset(); + Frames.reset(); SymFrames.reset(); - initRand(); Memory.reset(); + SymMemory.reset(); + initRand(); return std::monostate{}; } diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index cca614c6f..c75c02153 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -17,24 +17,30 @@ struct Num { Num(int64_t value) : value(value) {} Num() : value(0) {} int64_t value; - int32_t toInt() { return static_cast(value); } + int32_t toInt() const { return static_cast(value); } - bool operator==(const Num &other) const { return value == other.value; } + // TODO: support different bit width operations, for now we just assume all + // oprands are i32 + bool operator==(const Num &other) const { return toInt() == other.toInt(); } bool operator!=(const Num &other) const { return !(*this == other); } - Num operator+(const Num &other) const { return Num(value + other.value); } - Num operator-(const Num &other) const { return Num(value - other.value); } - Num operator*(const Num &other) const { return Num(value * other.value); } + Num operator+(const Num &other) const { return Num(toInt() + other.toInt()); } + Num operator-(const Num &other) const { return Num(toInt() - other.toInt()); } + Num operator*(const Num &other) const { return Num(toInt() * other.toInt()); } Num operator/(const Num &other) const { - if (other.value == 0) { + if (other.toInt() == 0) { throw std::runtime_error("Division by zero"); } - return Num(value / other.value); + return Num(toInt() / other.toInt()); } - Num operator<(const Num &other) const { return Num(value < other.value); } - Num operator<=(const Num &other) const { return Num(value <= other.value); } - Num operator>(const Num &other) const { return Num(value > other.value); } - Num operator>=(const Num &other) const { return Num(value >= other.value); } - Num operator&(const Num &other) const { return Num(value & other.value); } + Num operator<(const Num &other) const { return Num(toInt() < other.toInt()); } + Num operator<=(const Num &other) const { + return Num(toInt() <= other.toInt()); + } + Num operator>(const Num &other) const { return Num(toInt() > other.toInt()); } + Num operator>=(const Num &other) const { + return Num(toInt() >= other.toInt()); + } + Num operator&(const Num &other) const { return Num(toInt() & other.toInt()); } }; static Num I32V(int v) { return v; } @@ -71,8 +77,9 @@ class Stack_t { Profile.step(ProfileKind::POP); #ifdef DEBUG assert(count > 0 && "Stack underflow"); - printf("[Debug] popping from stack, size of concrete stack is: %d\n", - count); + printf("[Debug] popping a value %ld from stack, size of concrete stack is: " + "%d\n", + stack_ptr[count - 1].value, count); #endif Num num = stack_ptr[count - 1]; count--; @@ -223,6 +230,10 @@ struct Memory_t { page_count(init_page_count), allocated_pages(PRE_ALLOC_PAGES) {} int32_t loadInt(int32_t base, int32_t offset) { +#ifdef DEBUG + std::cout << "[Debug] loading int from memory at address: " + << (base + offset) << std::endl; +#endif // just load a 4-byte integer from memory of the vector int32_t addr = base + offset; if (!(addr + 3 < memory.size())) { @@ -238,8 +249,14 @@ struct Memory_t { std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { int32_t addr = base + offset; +#ifdef DEBUG + std::cout << "[Debug] storing int " << value << " to memory at address " + << addr << std::endl; +#endif // Ensure we don't write out of bounds - assert(addr + 3 < memory.size()); + if (!(addr + 3 < memory.size())) { + throw std::runtime_error("Invalid memory access " + std::to_string(addr)); + } for (int i = 0; i < 4; ++i) { memory[addr + i] = static_cast((value >> (8 * i)) & 0xFF); // Optionally, update memory[addr + i].second (SymVal) if needed diff --git a/headers/wasm/config.hpp b/headers/wasm/config.hpp new file mode 100644 index 000000000..48a546345 --- /dev/null +++ b/headers/wasm/config.hpp @@ -0,0 +1,36 @@ +#ifndef CONFIG_HPP +#define CONFIG_HPP + +// This file contains configuration settings for the concolic execution + +// If ENABLE_PROFILE defined, the compiled program will collect and print +// profiling information +#ifdef ENABLE_PROFILE +const bool PROFILE_ENABLED = true; +#else +const bool PROFILE_ENABLED = false; +#endif + +// This variable define when concolic execution will stop +enum class ExploreMode { + EarlyExit, // Stop at the first error encountered + + ExitByCoverage // Exit when all syntactic branches are covered +}; + +#ifdef EARLY_EXIT +static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; +#elif defined(BY_COVERAGE) +static const ExploreMode EXPLORE_MODE = ExploreMode::ExitByCoverage; +#else +static const ExploreMode EXPLORE_MODE = ExploreMode::EarlyExit; +#endif + +// This variable decides whether we enable the snapshot reuse optimization +#ifdef NO_REUSE +static const bool REUSE_SNAPSHOT = false; +#else +static const bool REUSE_SNAPSHOT = true; +#endif + +#endif // CONFIG_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index b112c932c..ec17448aa 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -2,6 +2,7 @@ #define PROFILE_HPP #include "utils.hpp" +#include "config.hpp" #include #include #include @@ -27,59 +28,57 @@ class Profile_t { public: Profile_t() : step_count(0) {} std::monostate step() { -#ifdef ENABLE_PROFILE - step_count++; -#endif + if (PROFILE_ENABLED) + step_count++; return std::monostate(); } std::monostate step(ProfileKind op) { -#ifdef ENABLE_PROFILE - op_count[static_cast(op)]++; -#endif + if (PROFILE_ENABLED) + op_count[static_cast(op)]++; return std::monostate(); } void print_summary() { -#ifdef ENABLE_PROFILE - std::cout << "Profile Summary:" << std::endl; - std::cout << "Total PUSH operations: " - << op_count[static_cast(ProfileKind::PUSH)] - << std::endl; - std::cout << "Total POP operations: " - << op_count[static_cast(ProfileKind::POP)] - << std::endl; - std::cout << "Total PEEK operations: " - << op_count[static_cast(ProfileKind::PEEK)] - << std::endl; - std::cout << "Total SHIFT operations: " - << op_count[static_cast(ProfileKind::SHIFT)] - << std::endl; - std::cout << "Total SET operations: " - << op_count[static_cast(ProfileKind::SET)] - << std::endl; - std::cout << "Total GET operations: " - << op_count[static_cast(ProfileKind::GET)] - << std::endl; - std::cout << "Total BINARY operations: " - << op_count[static_cast(ProfileKind::BINARY)] - << std::endl; - std::cout << "Total TREE_FILL operations: " - << op_count[static_cast(ProfileKind::TREE_FILL)] - << std::endl; - std::cout << "Total CURSOR_MOVE operations: " - << op_count[static_cast(ProfileKind::CURSOR_MOVE)] - << std::endl; - std::cout << "Total other instructions executed: " << step_count - << std::endl; - std::cout << "Total MEM_GROW operations: " - << op_count[static_cast(ProfileKind::MEM_GROW)] - << std::endl; - std::cout - << "Total SNAPSHOT_CREATE operations: " - << op_count[static_cast(ProfileKind::SNAPSHOT_CREATE)] - << std::endl; - std::cout << "Total time for instruction execution (s): " - << std::setprecision(15) << execution_time << std::endl; -#endif + if (PROFILE_ENABLED) { + std::cout << "Profile Summary:" << std::endl; + std::cout << "Total PUSH operations: " + << op_count[static_cast(ProfileKind::PUSH)] + << std::endl; + std::cout << "Total POP operations: " + << op_count[static_cast(ProfileKind::POP)] + << std::endl; + std::cout << "Total PEEK operations: " + << op_count[static_cast(ProfileKind::PEEK)] + << std::endl; + std::cout << "Total SHIFT operations: " + << op_count[static_cast(ProfileKind::SHIFT)] + << std::endl; + std::cout << "Total SET operations: " + << op_count[static_cast(ProfileKind::SET)] + << std::endl; + std::cout << "Total GET operations: " + << op_count[static_cast(ProfileKind::GET)] + << std::endl; + std::cout << "Total BINARY operations: " + << op_count[static_cast(ProfileKind::BINARY)] + << std::endl; + std::cout << "Total TREE_FILL operations: " + << op_count[static_cast(ProfileKind::TREE_FILL)] + << std::endl; + std::cout << "Total CURSOR_MOVE operations: " + << op_count[static_cast(ProfileKind::CURSOR_MOVE)] + << std::endl; + std::cout << "Total other instructions executed: " << step_count + << std::endl; + std::cout << "Total MEM_GROW operations: " + << op_count[static_cast(ProfileKind::MEM_GROW)] + << std::endl; + std::cout + << "Total SNAPSHOT_CREATE operations: " + << op_count[static_cast(ProfileKind::SNAPSHOT_CREATE)] + << std::endl; + std::cout << "Total time for instruction execution (s): " + << std::setprecision(15) << execution_time << std::endl; + } } // record the time spent in main instruction execution, in seconds diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 1cc3fb2d8..cc7c2d7b3 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -2,6 +2,7 @@ #define WASM_SYMBOLIC_RT_HPP #include "concrete_rt.hpp" +#include "config.hpp" #include "controls.hpp" #include "heap_mem_bookkeeper.hpp" #include "profile.hpp" @@ -29,12 +30,6 @@ class Symbolic { static int max_id = 0; -#ifdef NO_REUSE -static bool REUSE_MODE = false; -#else -static bool REUSE_MODE = true; -#endif - class Symbol : public Symbolic { public: // TODO: add type information to determine the size of bitvector @@ -265,8 +260,6 @@ class SymStack_t { stack.clear(); } - void reuse(Snapshot_t snapshot); - size_t size() const { return stack.size(); } SymVal operator[](size_t index) const { return stack[index]; } @@ -306,8 +299,6 @@ class SymFrames_t { stack.clear(); } - void reuse(Snapshot_t snapshot); - size_t size() const { return stack.size(); } SymVal operator[](size_t index) const { return stack[index]; } @@ -364,6 +355,11 @@ class SymMemory_t { memory[addr + 3] = s3; return std::monostate{}; } + + std::monostate reset() { + memory.clear(); + return std::monostate{}; + } }; static SymMemory_t SymMemory; @@ -371,7 +367,9 @@ static SymMemory_t SymMemory; // A snapshot of the symbolic state and execution context (control) class Snapshot_t { public: - explicit Snapshot_t(Cont_t cont, MCont_t mcont); + explicit Snapshot_t(Cont_t cont, MCont_t mcont, SymStack_t stack, + SymFrames_t frames, SymMemory_t memory); + explicit Snapshot_t() {} SymStack_t get_stack() const { return stack; } SymFrames_t get_frames() const { return frames; } @@ -388,31 +386,18 @@ class Snapshot_t { MCont_t mcont; }; -inline void SymStack_t::reuse(Snapshot_t snapshot) { -// Reusing the symbolic stack from the snapshot -#ifdef DEBUG - std::cout << "Reusing symbolic state from snapshot" << std::endl; - std::cout << "Old stack size = " << stack.size() << std::endl; - std::cout << "New stack size = " << snapshot.get_stack().stack.size() - << std::endl; -#endif - stack = snapshot.get_stack().stack; -} - -inline void SymFrames_t::reuse(Snapshot_t snapshot) { -// Reusing the symbolic frames from the snapshot -#ifdef DEBUG - std::cout << "Reusing symbolic state from snapshot" << std::endl; - std::cout << "Old frame size = " << stack.size() << std::endl; - std::cout << "New frame size = " << snapshot.get_frames().stack.size() - << std::endl; -#endif - stack = snapshot.get_frames().stack; -} - static SymFrames_t SymFrames; static SymFrames_t SymGlobals; +static Snapshot_t makeSnapshot(Cont_t cont, MCont_t mcont) { + if (REUSE_SNAPSHOT) { + return Snapshot_t(cont, mcont, SymStack, SymFrames, SymMemory); + } else { + // create a dummy snapshot, which will not be used + return Snapshot_t(); + } +} + struct Node; struct NodeBox { @@ -684,9 +669,10 @@ inline std::vector NodeBox::collect_path_conds() { return result; } -inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont) - : stack(SymStack), frames(SymFrames), memory(SymMemory), cont(cont), - mcont(mcont) { +inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont, SymStack_t stack, + SymFrames_t frames, SymMemory_t memory) + : stack(std::move(stack)), frames(std::move(frames)), + memory(std::move(memory)), cont(cont), mcont(mcont) { Profile.step(ProfileKind::SNAPSHOT_CREATE); #ifdef DEBUG std::cout << "Creating snapshot of size " << stack.size() << std::endl; @@ -740,11 +726,19 @@ class ExploreTree_t { "Can't move cursor when the branch node is not initialized correctly!"); if (branch) { true_branch_cov_map[if_else_node->id] = true; - if_else_node->false_branch->fillSnapshotNode(snapshot); + if (REUSE_SNAPSHOT) { + if_else_node->false_branch->fillSnapshotNode(snapshot); + } else { + // Do nothing, the initial value of the branch is an unexplored node + } cursor = if_else_node->true_branch.get(); } else { false_branch_cov_map[if_else_node->id] = true; - if_else_node->true_branch->fillSnapshotNode(snapshot); + if (REUSE_SNAPSHOT) { + if_else_node->true_branch->fillSnapshotNode(snapshot); + } else { + // Do nothing, the initial value of the branch is an unexplored node + } cursor = if_else_node->false_branch.get(); } @@ -884,7 +878,7 @@ static EvalRes eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { assert(high >= low && "Invalid extract range"); int size = high - low + 1; // size in bytes int64_t mask = (1LL << (size * 8)) - 1; - int64_t extracted_value = (res.value.toInt() >> (low * 8)) & mask; + int64_t extracted_value = (res.value.toInt() >> ((low - 1) * 8)) & mask; return EvalRes(Num(I64V(extracted_value)), size * 8); } else if (auto smallbv = dynamic_cast(sym.symptr.get())) { return EvalRes(Num(I64V(smallbv->get_value())), smallbv->get_size()); diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 86d86a8a7..c07ecbbce 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -344,11 +344,11 @@ trait StagedWasmEvaluator extends SAIOps { val id = Counter.getId(inst) ExploreTree.fillWithIfElse(symCond.s, id) def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info("Entering the true branch of the if") + info(s"Entering the true branch $id of the if") eval(thn, restK _, mk, restK _ :: trail)(newCtx) }) def elsK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info("Entering the false branch of the if") + info(s"Entering the false branch $id of the if") eval(els, restK _, mk, restK _ :: trail)(newCtx) }) if (cond.toInt != 0) { @@ -407,13 +407,13 @@ trait StagedWasmEvaluator extends SAIOps { // snapshotNode (this is done by moveCursor's runtime implementation) // TODO: store snapshot into this snapshot node def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info("Entering the true branch of the br_table") + info(s"Entering the true branch $id of the br_table") Stack.popC(ty) Stack.popS(ty) trail(choices.head)(newCtx)(mk) }) def elsK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info("Entering the false branch of the br_table") + info(s"Entering the false branch $id of the br_table") aux(choices.tail, idx + 1, mk) }) if (cond.toInt != 0) { @@ -1361,7 +1361,10 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { val argTypes = b.in.map(a => remap(typeMap(a))).mkString(", ") emitln(s"std::function<$retType(${argTypes})> ${quote(f)};") emit(quote(f)); emit(" = ") - quoteTypedBlock(b, false, true, capture = "&") + // We need to capture by value here, because we want to save a function in + // snapshot, and use the function later, while the local variables have + // been released. + quoteTypedBlock(b, false, true, capture = "=") emitln(";") case _ => super.traverse(n) } @@ -1386,7 +1389,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "sym-stack-pop", _, _) => emit("SymStack.pop()") case Node(_, "snapshot-make", List(k, mk), _) => - emit("Snapshot_t("); shallow(k); emit(", "); shallow(mk); emit(")") + emit("makeSnapshot("); shallow(k); emit(", "); shallow(mk); emit(")") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(")") case Node(_, "sym-frame-pop", List(i), _) => From ee9e57bedf0c7b43163c58bd13d2edd972bae6d0 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 5 Oct 2025 19:33:14 -0400 Subject: [PATCH 044/105] replace SymEnv_t's underlying representation --- headers/wasm/smt_solver.hpp | 7 ++----- headers/wasm/symbolic_rt.hpp | 20 ++++++++++---------- 2 files changed, 12 insertions(+), 15 deletions(-) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 64952bcc0..8625a65d1 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -14,7 +14,7 @@ class Solver { public: Solver() {} - std::optional> solve(const std::vector &conditions) { + std::optional solve(const std::vector &conditions) { // make an conjunction of all conditions z3::expr conjunction = z3_ctx.bool_val(true); for (const auto &cond : conditions) { @@ -33,7 +33,7 @@ class Solver { return std::nullopt; // No solution found case z3::sat: { z3::model model = z3_solver.get_model(); - std::vector result; + NumMap result; // Reference: // https://github.com/Z3Prover/z3/blob/master/examples/c%2B%2B/example.cpp#L59 GENSYM_INFO("Solved Z3 model"); @@ -44,9 +44,6 @@ class Solver { std::string name = var.name().str(); if (starts_with(name, "s_")) { int id = std::stoi(name.substr(2)); - if (id >= result.size()) { - result.resize(id + 1); - } result[id] = Num(value.get_numeral_int64()); } else { GENSYM_INFO("Find a variable that is not created by GenSym: " + name); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index cc7c2d7b3..8ecd207da 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -816,36 +816,36 @@ class ExploreTree_t { static ExploreTree_t ExploreTree; +using NumMap = std::unordered_map; + class SymEnv_t { public: Num read(const Symbol &symbol) { - if (symbol.get_id() >= map.size()) { - map.resize(symbol.get_id() + 1); - } #if DEBUG std::cout << "Read symbol: " << symbol.get_id() << " from symbolic environment" << std::endl; std::cout << "Current symbolic environment: " << to_string() << std::endl; #endif - - return map[symbol.get_id()]; + map.try_emplace(symbol.get_id(), Num(I32V(0))); + return map.at(symbol.get_id()); } Num read(SymVal sym) { + // Read the value of a symbolic value from the environment, it will update + // the environment if the key does not exist. auto symbol = dynamic_cast(sym.symptr.get()); assert(symbol); return read(*symbol); } - void update(std::vector new_env) { map = std::move(new_env); } + void update(NumMap new_env) { map = std::move(new_env); } std::string to_string() const { std::string result; result += "(\n"; - for (int i = 0; i < map.size(); ++i) { - const Num &num = map[i]; + for (const auto &[id, num] : map) { result += - " (" + std::to_string(i) + "->" + std::to_string(num.value) + ")\n"; + " (" + std::to_string(id) + "->" + std::to_string(num.value) + ")\n"; } result += ")"; return result; @@ -854,7 +854,7 @@ class SymEnv_t { size_t size() const { return map.size(); } private: - std::vector map; // The symbolic environment, a vector of Num + NumMap map; // The symbolic environment, a vector of Num }; static SymEnv_t SymEnv; From bd5036bcf41eee87dbef13e9f21bef9dd683e793 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 5 Oct 2025 19:53:13 -0400 Subject: [PATCH 045/105] compare the exploration trees (w/ vs. w/o snapshot reuse) --- .../genwasym/TestStagedConcolicEval.scala | 37 +++++++++++++++---- 1 file changed, 30 insertions(+), 7 deletions(-) diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index ada087ccf..a0877796c 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -12,15 +12,38 @@ class TestStagedConcolicEval extends FunSuite { def testFileConcolicCpp(filename: String, main: Option[String] = None, exitByCoverage: Boolean = false) = { + import sys.process._ + + val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" - val exe = s"$cppFile.exe" - val exploreTreeFile = s"$filename.tree.dot" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") - - import sys.process._ - val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! - println(result) + val exploreTreeFile = { + // Do concolic execution with snapshot reuse + val exe = s"$cppFile.exe" + val exploreTreeFile = s"$filename.tree.dot" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") + println(s"Running compiled concolic execution with snapshot reuse: $exe") + val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! + println(result) + exploreTreeFile + } + val exploreTreeFileNoReuse = { + // Do concolic execution without snapshot reuse + val exe = s"$cppFile.noreuse.exe" + val exploreTreeFile = s"$filename.noreuse.tree.dot" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, false, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") + println(s"Running compiled concolic execution without snapshot reuse: $exe") + val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! + println(result) + exploreTreeFile + } + // The explore tree generated by two executions should be same + import java.nio.file.Files + assert( + Files.readAllBytes(java.nio.file.Paths.get(exploreTreeFile)) + sameElements Files.readAllBytes(java.nio.file.Paths.get(exploreTreeFileNoReuse)), + s"Explore trees $exploreTreeFile and $exploreTreeFileNoReuse are different!" + ) } // only test concrete execution and its result From f63f682ec919535a9fa91b386ec3dda7a09acc4d Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 5 Oct 2025 20:01:48 -0400 Subject: [PATCH 046/105] accelerate test by using O0 optimization --- src/main/scala/wasm/StagedConcolicMiniWasm.scala | 3 ++- src/test/scala/genwasym/TestStagedConcolicEval.scala | 6 +++--- 2 files changed, 5 insertions(+), 4 deletions(-) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index c07ecbbce..739a0f39c 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -1590,6 +1590,7 @@ object WasmToCppCompiler { outputCpp: String, outputExe: String, printRes: Boolean, + optimizeLevel: Int, macros: String*): Unit = { val generated = compile(moduleInst, main, printRes) val code = generated.source @@ -1604,7 +1605,7 @@ object WasmToCppCompiler { import sys.process._ val includeFlags = generated.headerFolders.map(f => s"-I$f").mkString(" ") val macroFlags = macros.map(m => s"-D$m").mkString(" ") - val command = s"g++ -std=c++17 $outputCpp -o $outputExe -O3 -g -l z3 " + includeFlags + " " + macroFlags + val command = s"g++ -std=c++17 $outputCpp -o $outputExe -O$optimizeLevel -g -l z3 " + includeFlags + " " + macroFlags if (command.! != 0) { throw new RuntimeException(s"Compilation failed for $outputCpp") } diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index a0877796c..68009388a 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -21,7 +21,7 @@ class TestStagedConcolicEval extends FunSuite { // Do concolic execution with snapshot reuse val exe = s"$cppFile.exe" val exploreTreeFile = s"$filename.tree.dot" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") println(s"Running compiled concolic execution with snapshot reuse: $exe") val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! println(result) @@ -31,7 +31,7 @@ class TestStagedConcolicEval extends FunSuite { // Do concolic execution without snapshot reuse val exe = s"$cppFile.noreuse.exe" val exploreTreeFile = s"$filename.noreuse.tree.dot" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, false, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, false, optimizeLevel=0, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT") println(s"Running compiled concolic execution without snapshot reuse: $exe") val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! println(result) @@ -51,7 +51,7 @@ class TestStagedConcolicEval extends FunSuite { val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" val exe = s"$cppFile.exe" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, "NO_INFO", "RUN_ONCE") + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, "NO_INFO", "RUN_ONCE") import sys.process._ val result = s"./$exe".!! From e4ac385aa2b0ac2099b03790bf63cf3c525d6341 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 6 Oct 2025 21:54:54 -0400 Subject: [PATCH 047/105] add an option to use immutable data structure --- headers/wasm/config.hpp | 8 +++ headers/wasm/profile.hpp | 2 +- headers/wasm/symbolic_rt.hpp | 100 ++++++++++++++++++++++++++++++++--- 3 files changed, 103 insertions(+), 7 deletions(-) diff --git a/headers/wasm/config.hpp b/headers/wasm/config.hpp index 48a546345..9a34daad3 100644 --- a/headers/wasm/config.hpp +++ b/headers/wasm/config.hpp @@ -33,4 +33,12 @@ static const bool REUSE_SNAPSHOT = false; static const bool REUSE_SNAPSHOT = true; #endif +// If we use immutable data structures for symbolic states to reduce the cost of +// copying. +#ifdef USE_IMM +static const bool IMMUTABLE_SYMS = true; +#else +static const bool IMMUTABLE_SYMS = false; +#endif + #endif // CONFIG_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index ec17448aa..e453a386b 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -1,8 +1,8 @@ #ifndef PROFILE_HPP #define PROFILE_HPP -#include "utils.hpp" #include "config.hpp" +#include "utils.hpp" #include #include #include diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 8ecd207da..98a2a33aa 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -5,6 +5,9 @@ #include "config.hpp" #include "controls.hpp" #include "heap_mem_bookkeeper.hpp" +#include "immer/map.hpp" +#include "immer/map_transient.hpp" +#include "immer/vector_transient.hpp" #include "profile.hpp" #include "utils.hpp" #include @@ -238,26 +241,44 @@ class SymStack_t { printf("[Debug] poping from stack, size of symbolic stack is: %zu\n", stack.size()); #endif +#ifdef USE_IMM + auto ret = *(stack.end() - 1); + stack.take(stack.size() - 1); + return ret; +#else auto ret = stack.back(); stack.pop_back(); return ret; +#endif } - SymVal peek() { return stack.back(); } + SymVal peek() { return *(stack.end() - 1); } std::monostate shift(int32_t offset, int32_t size) { auto n = stack.size(); for (size_t i = n - size; i < n; ++i) { assert(i - offset >= 0); +#ifdef USE_IMM + stack.set(i - offset, stack[i]); +#else stack[i - offset] = stack[i]; +#endif } +#ifdef USE_IMM + stack.take(n - offset); +#else stack.resize(n - offset); +#endif return std::monostate(); } void reset() { - // Reset the symbolic stack +// Reset the symbolic stack +#ifdef USE_IMM + stack = immer::vector_transient(); +#else stack.clear(); +#endif } size_t size() const { return stack.size(); } @@ -265,20 +286,36 @@ class SymStack_t { SymVal operator[](size_t index) const { return stack[index]; } private: +#ifdef USE_IMM + immer::vector_transient stack; +#else std::vector stack; +#endif }; static SymStack_t SymStack; class SymFrames_t { + public: void pushFrame(int size) { // Push a new frame with the given size +#ifdef USE_IMM + for (int i = 0; i < size; ++i) { + stack.push_back(SymVal()); + } +#else stack.resize(size + stack.size()); +#endif } std::monostate popFrame(int size) { // Pop the frame of the given size + +#ifdef USE_IMM + stack.take(stack.size() - size); +#else stack.resize(stack.size() - size); +#endif return std::monostate(); } @@ -291,12 +328,21 @@ class SymFrames_t { void set(int index, SymVal val) { // Set the symbolic value at the given index assert(val.symptr != nullptr); +#ifdef USE_IMM + stack.set(stack.size() - 1 - index, val); +#else stack[stack.size() - 1 - index] = val; +#endif } void reset() { // Reset the symbolic frames + +#ifdef USE_IMM + stack = immer::vector_transient(); +#else stack.clear(); +#endif } size_t size() const { return stack.size(); } @@ -304,7 +350,11 @@ class SymFrames_t { SymVal operator[](size_t index) const { return stack[index]; } private: +#ifdef USE_IMM + immer::vector_transient stack; +#else std::vector stack; +#endif }; struct NodeBox; @@ -312,19 +362,45 @@ struct SymEnv_t; class SymMemory_t { public: +#ifdef USE_IMM + immer::map_transient memory; +#else std::unordered_map memory; +#endif SymVal loadSymByte(int32_t addr) { - // if the address is not in the memory, it must be a zero-initialized memory +// if the address is not in the memory, it must be a zero-initialized memory +#ifdef USE_IMM auto it = memory.find(addr); - SymVal s = (it != memory.end()) - ? it->second - : SymVal(SymBookKeeper.allocate(8, 0)); + if (it != nullptr) { + return *it; + } else { + auto s = SymVal(ZeroByte); + return s; + } +#else + auto it = memory.find(addr); + SymVal s = (it != memory.end()) ? it->second : SymVal(ZeroByte); return s; +#endif } SymVal loadSym(int32_t base, int32_t offset) { // calculate the real address + +#ifdef USE_IMM + int32_t addr = base + offset; + auto it = memory.find(addr); + SymVal s0 = it ? *it : SymVal(ZeroByte); + it = memory.find(addr + 1); + SymVal s1 = it ? *it : SymVal(ZeroByte); + it = memory.find(addr + 2); + SymVal s2 = it ? *it : SymVal(ZeroByte); + it = memory.find(addr + 3); + SymVal s3 = it ? *it : SymVal(ZeroByte); + + return s3.concat(s2).concat(s1).concat(s0); +#else int32_t addr = base + offset; auto it = memory.find(addr); SymVal s0 = (it != memory.end()) ? it->second : SymVal(ZeroByte); @@ -336,6 +412,7 @@ class SymMemory_t { SymVal s3 = (it != memory.end()) ? it->second : SymVal(ZeroByte); return s3.concat(s2).concat(s1).concat(s0); +#endif } // when loading a symval, we need to concat 4 symbolic values @@ -349,15 +426,26 @@ class SymMemory_t { SymVal s1 = value.extract(2, 2); SymVal s2 = value.extract(3, 3); SymVal s3 = value.extract(4, 4); +#ifdef USE_IMM + memory.set(addr, s0); + memory.set(addr + 1, s1); + memory.set(addr + 2, s2); + memory.set(addr + 3, s3); +#else memory[addr] = s0; memory[addr + 1] = s1; memory[addr + 2] = s2; memory[addr + 3] = s3; +#endif return std::monostate{}; } std::monostate reset() { +#ifdef USE_IMM + memory = immer::map_transient(); +#else memory.clear(); +#endif return std::monostate{}; } }; From 6bae60f4c11ac90f17464f34fc3fb2802ec29cf1 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 6 Oct 2025 22:48:18 -0400 Subject: [PATCH 048/105] a simple test case to show immutable's improvements --- .../wasm/staged/long-trivial-execution.wat | 54 +++++++++++++++++++ .../genwasym/TestStagedConcolicEval.scala | 21 +++++++- 2 files changed, 74 insertions(+), 1 deletion(-) create mode 100644 benchmarks/wasm/staged/long-trivial-execution.wat diff --git a/benchmarks/wasm/staged/long-trivial-execution.wat b/benchmarks/wasm/staged/long-trivial-execution.wat new file mode 100644 index 000000000..2a23f007f --- /dev/null +++ b/benchmarks/wasm/staged/long-trivial-execution.wat @@ -0,0 +1,54 @@ +(module + (type (;0;) (func)) + (type (;1;) (func (param i32))) + (import "console" "assert" (func (type 1))) + (func (;1;) (type 0) + (local i32 i32) + i32.const 1 + local.set 0 + i32.const 0 + local.set 1 + block + loop + local.get 0 + i32.const 10000 + i32.ge_s + br_if 1 + local.get 1 + i32.const 0 + i32.add + local.set 1 + local.get 0 + i32.const 1 + i32.add + local.set 0 + br 0 + end + end + i32.const 10000 + local.set 0 + i32.const 0 + local.set 1 + block + loop + local.get 0 + i32.eqz + br_if 1 ;; break if counter == 0 + local.get 1 + i32.const 0 + i32.sub ;; acc - 0 (no change) + local.set 1 + local.get 0 + i32.const 1 + i32.sub + local.set 0 ;; counter-- + br 0 ;; repeat loop + end + end + local.get 1 + if + i32.const 0 + call 0 + end + ) + (start 1)) diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 68009388a..6a505f140 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -37,6 +37,16 @@ class TestStagedConcolicEval extends FunSuite { println(result) exploreTreeFile } + val exploreTreeFileImm = { + // Do concolic execution with immutable data structure and snapshot reuse + val exe = s"$cppFile.imm.exe" + val exploreTreeFile = s"$filename.imm.tree.dot" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, if (exitByCoverage) "BY_COVERAGE" else "EARLY_EXIT", "USE_IMM") + println(s"Running compiled concolic execution with immutable data structure and snapshot reuse: $exe") + val result = Process(s"./$exe", None, "TREE_FILE" -> exploreTreeFile).!! + println(result) + exploreTreeFile + } // The explore tree generated by two executions should be same import java.nio.file.Files assert( @@ -44,6 +54,11 @@ class TestStagedConcolicEval extends FunSuite { sameElements Files.readAllBytes(java.nio.file.Paths.get(exploreTreeFileNoReuse)), s"Explore trees $exploreTreeFile and $exploreTreeFileNoReuse are different!" ) + assert( + Files.readAllBytes(java.nio.file.Paths.get(exploreTreeFile)) + sameElements Files.readAllBytes(java.nio.file.Paths.get(exploreTreeFileImm)), + s"Explore trees $exploreTreeFile and $exploreTreeFileImm are different!" + ) } // only test concrete execution and its result @@ -51,7 +66,7 @@ class TestStagedConcolicEval extends FunSuite { val moduleInst = ModuleInstance(Parser.parseFile(filename)) val cppFile = s"$filename.cpp" val exe = s"$cppFile.exe" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, "NO_INFO", "RUN_ONCE") + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, "NO_INFO", "RUN_ONCE", "USE_IMM") import sys.process._ val result = s"./$exe".!! @@ -98,6 +113,10 @@ class TestStagedConcolicEval extends FunSuite { } test("btree-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat", exitByCoverage = true) } + test("long-trivial-execution-concrete") { + // This is a example to show how much performance improvement we can get by immutable data structure + testFileConcreteCpp("./benchmarks/wasm/staged/long-trivial-execution.wat", None) + } test("return-poly - concrete") { testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) From 46b8a85da96132a027deb2f17cf0e4db2f40c429 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 12 Oct 2025 05:10:56 +0800 Subject: [PATCH 049/105] add a benchmark testcase --- benchmarks/wasm/compare_wasp/Makefile | 16 + benchmarks/wasm/compare_wasp/large-branch.wat | 591 ++++++++++++++++++ headers/wasm/concolic_driver.hpp | 3 +- headers/wasm/concrete_rt.hpp | 16 +- headers/wasm/config.hpp | 18 +- headers/wasm/profile.hpp | 90 ++- headers/wasm/smt_solver.hpp | 37 +- headers/wasm/symbolic_rt.hpp | 12 +- .../genwasym/TestStagedConcolicEval.scala | 3 + 9 files changed, 724 insertions(+), 62 deletions(-) create mode 100644 benchmarks/wasm/compare_wasp/Makefile create mode 100644 benchmarks/wasm/compare_wasp/large-branch.wat diff --git a/benchmarks/wasm/compare_wasp/Makefile b/benchmarks/wasm/compare_wasp/Makefile new file mode 100644 index 000000000..c9cc74ae1 --- /dev/null +++ b/benchmarks/wasm/compare_wasp/Makefile @@ -0,0 +1,16 @@ +.PHONY: all run clean + +all: large-branch.wat.cpp.imm.noreuse.exe large-branch.wat.cpp.imm.exe + +large-branch.wat.cpp.imm.noreuse.exe: large-branch.wat.cpp + g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.noreuse.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 -DNO_REUSE + +large-branch.wat.cpp.imm.exe: large-branch.wat.cpp + g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 + +run: all + ./large-branch.wat.cpp.imm.noreuse.exe + ./large-branch.wat.cpp.imm.exe + +clean: + rm -f *.exe \ No newline at end of file diff --git a/benchmarks/wasm/compare_wasp/large-branch.wat b/benchmarks/wasm/compare_wasp/large-branch.wat new file mode 100644 index 000000000..76e40191c --- /dev/null +++ b/benchmarks/wasm/compare_wasp/large-branch.wat @@ -0,0 +1,591 @@ +(module + (type (;0;) (func (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32))) + (type (;1;) (func (result i32))) + (import "spectest" "print_i32" (func (;0;) (param i32))) + + (func (;1;) (type 0) (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32) + local.get 0 + i32.const 0 + i32.gt_s + if ;; label = @1 + local.get 7 + local.get 13 + i32.add + i32.const 13 + i32.add + local.set 0 + end + local.get 1 + i32.const 1 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 7 + i32.add + i32.const 35 + i32.add + local.set 1 + end + local.get 2 + i32.const 2 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 4 + i32.add + i32.const 69 + i32.add + local.set 2 + end + local.get 3 + i32.const 3 + i32.gt_s + if ;; label = @1 + local.get 13 + local.get 14 + i32.add + i32.const 91 + i32.add + local.set 3 + end + local.get 4 + i32.const 4 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 10 + i32.add + i32.const 47 + i32.add + local.set 4 + end + local.get 5 + i32.const 5 + i32.gt_s + if ;; label = @1 + local.get 15 + local.get 6 + i32.add + i32.const 74 + i32.add + local.set 5 + end + local.get 6 + i32.const 6 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 8 + i32.add + i32.const 15 + i32.add + local.set 6 + end + local.get 7 + i32.const 7 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 9 + i32.add + i32.const 34 + i32.add + local.set 7 + end + local.get 8 + i32.const 8 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 12 + i32.add + i32.const 57 + i32.add + local.set 8 + end + local.get 9 + i32.const 9 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 11 + i32.add + i32.const 3 + i32.add + local.set 9 + end + local.get 10 + i32.const 10 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 6 + i32.add + i32.const 21 + i32.add + local.set 10 + end + local.get 11 + i32.const 11 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 5 + i32.add + i32.const 72 + i32.add + local.set 11 + end + local.get 12 + i32.const 12 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 6 + i32.add + i32.const 55 + i32.add + local.set 12 + end + local.get 13 + i32.const 13 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 3 + i32.add + i32.const 12 + i32.add + local.set 13 + end + local.get 14 + i32.const 14 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 12 + i32.add + i32.const 69 + i32.add + local.set 14 + end + local.get 15 + i32.const 15 + i32.gt_s + if ;; label = @1 + local.get 18 + local.get 5 + i32.add + i32.const 92 + i32.add + local.set 15 + end + local.get 16 + i32.const 16 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 12 + i32.add + i32.const 39 + i32.add + local.set 16 + end + local.get 17 + i32.const 17 + i32.gt_s + if ;; label = @1 + local.get 15 + local.get 8 + i32.add + i32.const 39 + i32.add + local.set 17 + end + local.get 18 + i32.const 18 + i32.gt_s + if ;; label = @1 + local.get 17 + local.get 3 + i32.add + i32.const 64 + i32.add + local.set 18 + end + local.get 19 + i32.const 19 + i32.gt_s + if ;; label = @1 + local.get 11 + local.get 5 + i32.add + i32.const 78 + i32.add + local.set 19 + end + local.get 6 + i32.const 6 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 8 + i32.add + i32.const 15 + i32.add + local.set 6 + end + local.get 7 + i32.const 7 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 9 + i32.add + i32.const 34 + i32.add + local.set 7 + end + local.get 8 + i32.const 8 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 12 + i32.add + i32.const 57 + i32.add + local.set 8 + end + local.get 9 + i32.const 9 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 11 + i32.add + i32.const 3 + i32.add + local.set 9 + end + local.get 10 + i32.const 10 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 6 + i32.add + i32.const 21 + i32.add + local.set 10 + end + local.get 11 + i32.const 11 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 5 + i32.add + i32.const 72 + i32.add + local.set 11 + end + local.get 12 + i32.const 12 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 6 + i32.add + i32.const 55 + i32.add + local.set 12 + end + local.get 13 + i32.const 13 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 3 + i32.add + i32.const 12 + i32.add + local.set 13 + end + local.get 14 + i32.const 14 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 12 + i32.add + i32.const 69 + i32.add + local.set 14 + end + local.get 15 + i32.const 15 + i32.gt_s + if ;; label = @1 + local.get 18 + local.get 5 + i32.add + i32.const 92 + i32.add + local.set 15 + end + local.get 16 + i32.const 16 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 12 + i32.add + i32.const 39 + i32.add + local.set 16 + end + local.get 1 + local.get 2 + i32.add + local.get 3 + i32.add + local.get 4 + i32.add + local.get 5 + i32.add + local.get 6 + i32.add + local.get 7 + i32.add + local.get 8 + i32.add + local.get 9 + i32.add + local.get 10 + i32.add + local.get 11 + i32.add + local.get 12 + i32.add + local.get 13 + i32.add + local.get 14 + i32.add + local.get 15 + i32.add + local.get 16 + i32.add + local.get 17 + i32.add + local.get 18 + i32.add + local.get 19 + i32.add) + (func (;2;) (type 1) (result i32) + i32.const 0 + i32.symbolic + i32.const 1 + i32.symbolic + i32.const 2 + i32.symbolic + i32.const 3 + i32.symbolic + i32.const 4 + i32.symbolic + i32.const 5 + i32.symbolic + i32.const 6 + i32.symbolic + i32.const 7 + i32.symbolic + i32.const 8 + i32.symbolic + i32.const 9 + i32.symbolic + i32.const 10 + i32.const 11 + i32.const 12 + i32.const 13 + i32.const 14 + i32.const 15 + i32.const 16 + i32.const 17 + i32.const 18 + i32.const 19 + call 3) + (func (;3;) (type 0) (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32) + local.get 0 + i32.const 0 + i32.gt_s + if ;; label = @1 + local.get 7 + local.get 13 + i32.add + i32.const 13 + i32.add + local.set 0 + end + local.get 1 + i32.const 1 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 7 + i32.add + i32.const 35 + i32.add + local.set 1 + end + local.get 2 + i32.const 2 + i32.gt_s + if ;; label = @1 + local.get 0 + local.get 4 + i32.add + i32.const 69 + i32.add + local.set 2 + end + local.get 3 + i32.const 3 + i32.gt_s + if ;; label = @1 + local.get 13 + local.get 14 + i32.add + i32.const 91 + i32.add + local.set 3 + end + local.get 4 + i32.const 4 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 10 + i32.add + i32.const 47 + i32.add + local.set 4 + end + local.get 5 + i32.const 5 + i32.gt_s + if ;; label = @1 + local.get 15 + local.get 6 + i32.add + i32.const 74 + i32.add + local.set 5 + end + local.get 6 + i32.const 6 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 8 + i32.add + i32.const 15 + i32.add + local.set 6 + end + local.get 6 + i32.const 6 + i32.gt_s + if ;; label = @1 + local.get 19 + local.get 8 + i32.add + i32.const 15 + i32.add + local.set 6 + end + local.get 7 + i32.const 7 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 9 + i32.add + i32.const 34 + i32.add + local.set 7 + end + local.get 8 + i32.const 8 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 12 + i32.add + i32.const 57 + i32.add + local.set 8 + end + local.get 9 + i32.const 9 + i32.gt_s + if ;; label = @1 + local.get 10 + local.get 11 + i32.add + i32.const 3 + i32.add + local.set 9 + end + local.get 10 + i32.const 10 + i32.gt_s + if ;; label = @1 + local.get 6 + local.get 6 + i32.add + i32.const 21 + i32.add + local.set 10 + end + local.get 1 + local.get 2 + i32.add + local.get 3 + i32.add + local.get 4 + i32.add + local.get 5 + i32.add + local.get 6 + i32.add + local.get 7 + i32.add + local.get 8 + i32.add + local.get 9 + i32.add + local.get 10 + i32.add + local.get 11 + i32.add + local.get 12 + i32.add + local.get 13 + i32.add + local.get 14 + i32.add + local.get 15 + i32.add + local.get 16 + i32.add + local.get 17 + i32.add + local.get 18 + i32.add + local.get 19 + i32.add + ) + (export "f" (func 1)) + (export "main" (func 2)) + (start 2)) + diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 37ef4004c..84e05c844 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -100,10 +100,9 @@ inline void ConcolicDriver::main_exploration_loop() { GENSYM_INFO(SymEnv.to_string()); if (auto snapshot_node = dynamic_cast(node->node.get())) { assert(REUSE_SNAPSHOT); - auto timer = ManagedTimer(); snapshot_node->get_snapshot().resume_execution(SymEnv, node); } else { - auto timer = ManagedTimer(); + auto timer = ManagedTimer(TimeProfileKind::INSTR); reset_stacks(); ExploreTree.reset_cursor(); entrypoint(); diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index c75c02153..ea321f456 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -60,21 +60,21 @@ class Stack_t { } std::monostate push(Num &&num) { - Profile.step(ProfileKind::PUSH); + Profile.step(StepProfileKind::PUSH); stack_ptr[count] = num; count++; return std::monostate{}; } std::monostate push(Num &num) { - Profile.step(ProfileKind::PUSH); + Profile.step(StepProfileKind::PUSH); stack_ptr[count] = num; count++; return std::monostate{}; } Num pop() { - Profile.step(ProfileKind::POP); + Profile.step(StepProfileKind::POP); #ifdef DEBUG assert(count > 0 && "Stack underflow"); printf("[Debug] popping a value %ld from stack, size of concrete stack is: " @@ -87,7 +87,7 @@ class Stack_t { } Num peek() { - Profile.step(ProfileKind::PEEK); + Profile.step(StepProfileKind::PEEK); #ifdef DEBUG if (count == 0) { throw std::runtime_error("Stack underflow"); @@ -99,7 +99,7 @@ class Stack_t { int32_t size() { return count; } void shift(int32_t offset, int32_t size) { - Profile.step(ProfileKind::SHIFT); + Profile.step(StepProfileKind::SHIFT); #ifdef DEBUG if (offset < 0) { throw std::out_of_range("Invalid offset: " + std::to_string(offset)); @@ -168,13 +168,13 @@ class Frames_t { } Num get(std::int32_t index) { - Profile.step(ProfileKind::GET); + Profile.step(StepProfileKind::GET); auto ret = stack_ptr[count - 1 - index]; return ret; } void set(std::int32_t index, Num num) { - Profile.step(ProfileKind::SET); + Profile.step(StepProfileKind::SET); stack_ptr[count - 1 - index] = num; } @@ -273,7 +273,7 @@ struct Memory_t { // grow memory by delta bytes when bytes > 0. return -1 if failed, return old // size when success int32_t grow(int32_t delta) { - Profile.step(ProfileKind::MEM_GROW); + Profile.step(StepProfileKind::MEM_GROW); if (delta <= 0) { return page_count * pagesize; } diff --git a/headers/wasm/config.hpp b/headers/wasm/config.hpp index 9a34daad3..76be60acb 100644 --- a/headers/wasm/config.hpp +++ b/headers/wasm/config.hpp @@ -3,12 +3,20 @@ // This file contains configuration settings for the concolic execution -// If ENABLE_PROFILE defined, the compiled program will collect and print -// profiling information -#ifdef ENABLE_PROFILE -const bool PROFILE_ENABLED = true; +// If ENABLE_PROFILE_STEP defined, the compiled program will collect and print +// profiling how much steps of each data structure's operations are executed +#ifdef ENABLE_PROFILE_STEP +const bool PROFILE_STEP = true; #else -const bool PROFILE_ENABLED = false; +const bool PROFILE_STEP = false; +#endif + +// If ENABLE_PROFILE_TIME defined, the compiled program will collect and print +// the profile of time spent in main loop and constraint solving +#ifdef ENABLE_PROFILE_TIME +const bool PROFILE_TIME = true; +#else +const bool PROFILE_TIME = false; #endif // This variable define when concolic execution will stop diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index e453a386b..ee0bef38f 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -8,7 +8,7 @@ #include #include -enum class ProfileKind { +enum class StepProfileKind { PUSH, POP, PEEK, @@ -24,74 +24,100 @@ enum class ProfileKind { // number of kinds of operations }; +enum class TimeProfileKind { + INSTR, + SOLVER, + RESUME_SNAPSHOT, + TimeOperationCount // keep this as the last element, this is used to get the + // number of kinds of operations +}; + class Profile_t { public: Profile_t() : step_count(0) {} std::monostate step() { - if (PROFILE_ENABLED) + if (PROFILE_STEP) step_count++; return std::monostate(); } - std::monostate step(ProfileKind op) { - if (PROFILE_ENABLED) + std::monostate step(StepProfileKind op) { + if (PROFILE_STEP) op_count[static_cast(op)]++; return std::monostate(); } void print_summary() { - if (PROFILE_ENABLED) { + if (PROFILE_STEP) { std::cout << "Profile Summary:" << std::endl; std::cout << "Total PUSH operations: " - << op_count[static_cast(ProfileKind::PUSH)] + << op_count[static_cast(StepProfileKind::PUSH)] << std::endl; std::cout << "Total POP operations: " - << op_count[static_cast(ProfileKind::POP)] + << op_count[static_cast(StepProfileKind::POP)] << std::endl; std::cout << "Total PEEK operations: " - << op_count[static_cast(ProfileKind::PEEK)] + << op_count[static_cast(StepProfileKind::PEEK)] << std::endl; std::cout << "Total SHIFT operations: " - << op_count[static_cast(ProfileKind::SHIFT)] + << op_count[static_cast(StepProfileKind::SHIFT)] << std::endl; std::cout << "Total SET operations: " - << op_count[static_cast(ProfileKind::SET)] + << op_count[static_cast(StepProfileKind::SET)] << std::endl; std::cout << "Total GET operations: " - << op_count[static_cast(ProfileKind::GET)] + << op_count[static_cast(StepProfileKind::GET)] << std::endl; std::cout << "Total BINARY operations: " - << op_count[static_cast(ProfileKind::BINARY)] - << std::endl; - std::cout << "Total TREE_FILL operations: " - << op_count[static_cast(ProfileKind::TREE_FILL)] - << std::endl; - std::cout << "Total CURSOR_MOVE operations: " - << op_count[static_cast(ProfileKind::CURSOR_MOVE)] + << op_count[static_cast(StepProfileKind::BINARY)] << std::endl; + std::cout + << "Total TREE_FILL operations: " + << op_count[static_cast(StepProfileKind::TREE_FILL)] + << std::endl; + std::cout + << "Total CURSOR_MOVE operations: " + << op_count[static_cast(StepProfileKind::CURSOR_MOVE)] + << std::endl; std::cout << "Total other instructions executed: " << step_count << std::endl; std::cout << "Total MEM_GROW operations: " - << op_count[static_cast(ProfileKind::MEM_GROW)] + << op_count[static_cast(StepProfileKind::MEM_GROW)] + << std::endl; + std::cout << "Total SNAPSHOT_CREATE operations: " + << op_count[static_cast( + StepProfileKind::SNAPSHOT_CREATE)] << std::endl; - std::cout - << "Total SNAPSHOT_CREATE operations: " - << op_count[static_cast(ProfileKind::SNAPSHOT_CREATE)] - << std::endl; std::cout << "Total time for instruction execution (s): " << std::setprecision(15) << execution_time << std::endl; } + if (PROFILE_TIME) { + std::cout << "Time Profile Summary:" << std::endl; + std::cout << "Total time in instruction execution (s): " + << std::setprecision(15) + << time_count[static_cast(TimeProfileKind::INSTR)] + << std::endl; + std::cout << "Total time in solver (s): " << std::setprecision(15) + << time_count[static_cast(TimeProfileKind::SOLVER)] + << std::endl; + std::cout << "Total time in resuming from snapshot (s): " + << std::setprecision(15) + << time_count[static_cast( + TimeProfileKind::RESUME_SNAPSHOT)] + << std::endl; + } } // record the time spent in main instruction execution, in seconds - void add_instruction_time(double time) { -#ifdef ENABLE_PROFILE - execution_time += time; -#endif + void add_instruction_time(TimeProfileKind kind, double time) { + time_count[static_cast(kind)] += time; } private: int step_count; - std::array(ProfileKind::OperationCount)> + std::array(StepProfileKind::OperationCount)> op_count; + std::array(TimeProfileKind::TimeOperationCount)> + time_count; double execution_time = 0.0; }; @@ -99,14 +125,18 @@ static Profile_t Profile; class ManagedTimer { public: - ManagedTimer() { start = std::chrono::high_resolution_clock::now(); } + ManagedTimer() = delete; + ManagedTimer(TimeProfileKind kind) : kind(kind) { + start = std::chrono::high_resolution_clock::now(); + } ~ManagedTimer() { auto end = std::chrono::high_resolution_clock::now(); std::chrono::duration elapsed = end - start; - Profile.add_instruction_time(elapsed.count()); + Profile.add_instruction_time(kind, elapsed.count()); } private: + TimeProfileKind kind; std::chrono::high_resolution_clock::time_point start; }; diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 8625a65d1..5df683f76 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -4,6 +4,7 @@ #include "concrete_rt.hpp" #include "symbolic_rt.hpp" #include "utils.hpp" +#include "wasm/profile.hpp" #include "z3++.h" #include #include @@ -15,20 +16,17 @@ class Solver { public: Solver() {} std::optional solve(const std::vector &conditions) { - // make an conjunction of all conditions - z3::expr conjunction = z3_ctx.bool_val(true); - for (const auto &cond : conditions) { - auto z3_cond = build_z3_expr(cond); - conjunction = conjunction && z3_cond != z3_ctx.bv_val(0, 32); - } -#ifdef DEBUG - std::cout << "Symbolic conditions size: " << conditions.size() << std::endl; - std::cout << "Solving conditions: " << conjunction << std::endl; -#endif - // call z3 to solve the condition z3::solver z3_solver(z3_ctx); - z3_solver.add(conjunction); - switch (z3_solver.check()) { + z3::check_result solver_result; + { + // make an conjunction of all conditions + auto conjunction = to_z3_conjunction(conditions); + // call z3 to solve the condition + auto timer = ManagedTimer(TimeProfileKind::SOLVER); + z3_solver.add(conjunction); // NOTE: half of the solver time is spent in solver.add + solver_result = z3_solver.check(); + } + switch (solver_result) { case z3::unsat: return std::nullopt; // No solution found case z3::sat: { @@ -58,6 +56,19 @@ class Solver { } private: + z3::expr to_z3_conjunction(const std::vector &conditions) { + z3::expr conjunction = z3_ctx.bool_val(true); + for (const auto &cond : conditions) { + auto z3_cond = build_z3_expr(cond); + conjunction = conjunction && z3_cond != z3_ctx.bv_val(0, 32); + } +#ifdef DEBUG + std::cout << "Symbolic conditions size: " << conditions.size() << std::endl; + std::cout << "Solving conditions: " << conjunction << std::endl; +#endif + return conjunction; + } + z3::context z3_ctx; z3::expr build_z3_expr(const SymVal &sym_val); }; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 98a2a33aa..35e19bd81 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -761,7 +761,7 @@ inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont, SymStack_t stack, SymFrames_t frames, SymMemory_t memory) : stack(std::move(stack)), frames(std::move(frames)), memory(std::move(memory)), cont(cont), mcont(mcont) { - Profile.step(ProfileKind::SNAPSHOT_CREATE); + Profile.step(StepProfileKind::SNAPSHOT_CREATE); #ifdef DEBUG std::cout << "Creating snapshot of size " << stack.size() << std::endl; #endif @@ -806,7 +806,7 @@ class ExploreTree_t { } std::monostate moveCursor(bool branch, Snapshot_t snapshot) { - Profile.step(ProfileKind::CURSOR_MOVE); + Profile.step(StepProfileKind::CURSOR_MOVE); assert(cursor != nullptr); auto if_else_node = dynamic_cast(cursor->node.get()); assert( @@ -1074,9 +1074,13 @@ inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, SymStack = stack; SymFrames = frames; SymMemory = memory; - // Restore the concrete states from the symbolic states - resume_conc_states(stack, frames, memory, Stack, Frames, Memory, sym_env); + { + auto timer = ManagedTimer(TimeProfileKind::RESUME_SNAPSHOT); + // Restore the concrete states from the symbolic states + resume_conc_states(stack, frames, memory, Stack, Frames, Memory, sym_env); + } // Resume execution from the continuation + auto timer = ManagedTimer(TimeProfileKind::INSTR); return cont(mcont); } diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 6a505f140..3bee9f751 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -171,4 +171,7 @@ class TestStagedConcolicEval extends FunSuite { testFileConcreteCpp("./benchmarks/wasm/staged/brtable.wat") } + test("large-branch-concrete") { + testFileConcreteCpp("./benchmarks/wasm/compare_wasp/large-branch.wat") + } } From db4925140d7df371bb25ec6fce1ff8be08d5f868 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 12 Oct 2025 06:12:50 +0800 Subject: [PATCH 050/105] a pool to store symbolic concrete --- headers/wasm/symbolic_rt.hpp | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 35e19bd81..798adf4d7 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -120,8 +120,16 @@ static SymVal make_symbolic(int index) { return SymVal(SymBookKeeper.allocate(index)); } +static std::unordered_map concrete_pool; + inline SymVal Concrete(Num num) { - return SymVal(SymBookKeeper.allocate(num)); + if (concrete_pool.find(num.toInt()) != concrete_pool.end()) { + return concrete_pool[num.toInt()]; + } + + auto new_val = SymVal(SymBookKeeper.allocate(num)); + concrete_pool[num.toInt()] = new_val; + return new_val; } // Extract is different from other operations, it only has one symbolic operand, From b4d18ba03bc2a08dd0471fab89ce43779f92704f Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sun, 12 Oct 2025 06:16:36 +0800 Subject: [PATCH 051/105] a example to show when snapshot is highly effective --- .../wasm/compare_wasp/small-snapshot.wat | 22301 ++++++++++++++++ .../genwasym/TestStagedConcolicEval.scala | 4 + 2 files changed, 22305 insertions(+) create mode 100644 benchmarks/wasm/compare_wasp/small-snapshot.wat diff --git a/benchmarks/wasm/compare_wasp/small-snapshot.wat b/benchmarks/wasm/compare_wasp/small-snapshot.wat new file mode 100644 index 000000000..991a3d250 --- /dev/null +++ b/benchmarks/wasm/compare_wasp/small-snapshot.wat @@ -0,0 +1,22301 @@ +(module + (type (;0;) (func (param i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32 i32) (result i32))) + (type (;1;) (func (result i32))) + (import "spectest" "print_i32" (func (;0;) (param i32))) + + (func (;1;) (type 0) (result i32) + i32.const 0 + i32.symbolic + call 2 + if (result i32) + i32.const 42 + else + i32.const 19 + end) + + (func (;2;) (param i32) (result i32) + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + i32.const 3 + drop + local.get 0) + (export "f" (func 2)) + (export "main" (func 1)) + (start 1)) + diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 3bee9f751..86f55daa2 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -174,4 +174,8 @@ class TestStagedConcolicEval extends FunSuite { test("large-branch-concrete") { testFileConcreteCpp("./benchmarks/wasm/compare_wasp/large-branch.wat") } + + test("small-snapshot-concrete") { + testFileConcreteCpp("./benchmarks/wasm/compare_wasp/small-snapshot.wat", Some("main")) + } } From 960aacbb51fbce95c16c9f4abfebbe4910a713b6 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 18 Oct 2025 19:47:47 +0800 Subject: [PATCH 052/105] some infra to support the cost model to decide if we should create snapshot --- headers/wasm/concolic_driver.hpp | 26 +-- headers/wasm/config.hpp | 6 + headers/wasm/controls.hpp | 7 + headers/wasm/profile.hpp | 27 +++ headers/wasm/symbolic_rt.hpp | 201 +++++++++++++++--- .../scala/wasm/StagedConcolicMiniWasm.scala | 61 ++++-- 6 files changed, 261 insertions(+), 67 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 84e05c844..80ff38d5f 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -84,6 +84,11 @@ inline void ConcolicDriver::main_exploration_loop() { continue; } + if (INTERACTIVE_MODE) { + std::cout << "Press Enter to continue to the next path..." << std::endl; + std::cin.get(); + } + auto cond = node->collect_path_conds(); auto result = solver.solve(cond); if (!result.has_value()) { @@ -98,15 +103,7 @@ inline void ConcolicDriver::main_exploration_loop() { try { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); - if (auto snapshot_node = dynamic_cast(node->node.get())) { - assert(REUSE_SNAPSHOT); - snapshot_node->get_snapshot().resume_execution(SymEnv, node); - } else { - auto timer = ManagedTimer(TimeProfileKind::INSTR); - reset_stacks(); - ExploreTree.reset_cursor(); - entrypoint(); - } + { node->reach_here(entrypoint); } GENSYM_INFO("Execution finished successfully with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); @@ -140,17 +137,6 @@ inline void ConcolicDriver::run() { Profile.print_summary(); } -static std::monostate reset_stacks() { - Stack.reset(); - SymStack.reset(); - Frames.reset(); - SymFrames.reset(); - Memory.reset(); - SymMemory.reset(); - initRand(); - return std::monostate{}; -} - static void start_concolic_execution_with( std::function entrypoint, int branchCount) { diff --git a/headers/wasm/config.hpp b/headers/wasm/config.hpp index 76be60acb..a9c8d5a12 100644 --- a/headers/wasm/config.hpp +++ b/headers/wasm/config.hpp @@ -49,4 +49,10 @@ static const bool IMMUTABLE_SYMS = true; static const bool IMMUTABLE_SYMS = false; #endif +#ifdef INTERACTIVE +static const bool INTERACTIVE_MODE = true; +#else +static const bool INTERACTIVE_MODE = false; +#endif + #endif // CONFIG_HPP \ No newline at end of file diff --git a/headers/wasm/controls.hpp b/headers/wasm/controls.hpp index 513f06924..97ba0130f 100644 --- a/headers/wasm/controls.hpp +++ b/headers/wasm/controls.hpp @@ -9,4 +9,11 @@ using MCont_t = std::function; using Cont_t = std::function; +struct Control { + Cont_t cont; + MCont_t mcont; + + Control(Cont_t cont, MCont_t mcont) : cont(cont), mcont(mcont) {} +}; + #endif // WASM_CONTROLS_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index ee0bef38f..bc4ce911d 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -28,6 +28,7 @@ enum class TimeProfileKind { INSTR, SOLVER, RESUME_SNAPSHOT, + COUNT_SYM_SIZE, TimeOperationCount // keep this as the last element, this is used to get the // number of kinds of operations }; @@ -103,6 +104,11 @@ class Profile_t { << time_count[static_cast( TimeProfileKind::RESUME_SNAPSHOT)] << std::endl; + std::cout << "Total time in counting symbolic size (s): " + << std::setprecision(15) + << time_count[static_cast( + TimeProfileKind::COUNT_SYM_SIZE)] + << std::endl; } } @@ -140,4 +146,25 @@ class ManagedTimer { std::chrono::high_resolution_clock::time_point start; }; +struct CostManager_t { + int instr_cost; + + CostManager_t() : instr_cost(0) {} + + std::monostate add_instr_cost(int n) { + instr_cost += n; + return {}; + } + + int dump_instr_cost() { + auto cost = instr_cost; + instr_cost = 0; + return normalize_cost(cost); + } + + int normalize_cost(int cost) { return 1 * cost; } +}; + +static CostManager_t CostManager; + #endif // PROFILE_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 798adf4d7..1423dcf16 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -27,8 +27,9 @@ class Symbolic { public: - Symbolic() {} // TODO: remove this default constructor later + Symbolic() {} virtual ~Symbolic() = default; // Make Symbolic polymorphic + virtual int size() = 0; }; static int max_id = 0; @@ -39,6 +40,7 @@ class Symbol : public Symbolic { // for now we just assume that only i32 will be used Symbol(int id) : id(id) { max_id = std::max(max_id, id); } int get_id() const { return id; } + int size() override { return 1; } private: int id; @@ -48,16 +50,18 @@ class SymConcrete : public Symbolic { public: Num value; SymConcrete(Num num) : value(num) {} + int size() override { return 1; } }; class SmallBV : public Symbolic { public: - SmallBV(int size, int64_t value) : size(size), value(value) {} - int get_size() const { return size; } + SmallBV(int width, int64_t value) : width(width), value(value) {} + int get_size() const { return width; } int64_t get_value() const { return value; } + int size() override { return 1; } private: - int size; // in bits + int width; // in bits int64_t value; }; struct SymBinary; @@ -111,6 +115,7 @@ struct SymVal { // TODO: add bitwise operations, and use the underlying bitvector theory bool is_concrete() const; + int size() const { return symptr->size(); } private: static SymVal make_binary(Operation op, const SymVal &lhs, const SymVal &rhs); @@ -142,6 +147,7 @@ struct SymExtract : Symbolic { SymExtract(SymVal value, int high, int low) : value(value), high(high), low(low) {} + int size() override { return 1 + value.size(); } }; struct SymBinary : Symbolic { @@ -151,6 +157,7 @@ struct SymBinary : Symbolic { SymBinary(Operation op, SymVal lhs, SymVal rhs) : op(op), lhs(lhs), rhs(rhs) {} + int size() override { return 1 + lhs.size() + rhs.size(); } }; inline SymVal SymVal::add(const SymVal &other) const { @@ -293,6 +300,14 @@ class SymStack_t { SymVal operator[](size_t index) const { return stack[index]; } + int cost_of_copy() const { + int cost = 0; + for (size_t i = 0; i < stack.size(); ++i) { + cost += stack[i].size(); + } + return cost; + } + private: #ifdef USE_IMM immer::vector_transient stack; @@ -357,6 +372,14 @@ class SymFrames_t { SymVal operator[](size_t index) const { return stack[index]; } + int cost_of_copy() const { + int cost = 0; + for (size_t i = 0; i < stack.size(); ++i) { + cost += stack[i].size(); + } + return cost; + } + private: #ifdef USE_IMM immer::vector_transient stack; @@ -456,6 +479,15 @@ class SymMemory_t { #endif return std::monostate{}; } + + int cost_of_copy() const { +#ifdef USE_IMM + // If we use immer, the copy cost should be negligible + return 0; +#else + return memory.size(); +#endif + } }; static SymMemory_t SymMemory; @@ -471,7 +503,9 @@ class Snapshot_t { SymFrames_t get_frames() const { return frames; } SymMemory_t get_memory() const { return memory; } - std::monostate resume_execution(SymEnv_t &sym_env, NodeBox *node) const; + std::monostate resume_execution(NodeBox *node) const; + + static int cost_of_snapshot(); private: SymStack_t stack; @@ -485,13 +519,14 @@ class Snapshot_t { static SymFrames_t SymFrames; static SymFrames_t SymGlobals; -static Snapshot_t makeSnapshot(Cont_t cont, MCont_t mcont) { - if (REUSE_SNAPSHOT) { - return Snapshot_t(cont, mcont, SymStack, SymFrames, SymMemory); - } else { - // create a dummy snapshot, which will not be used - return Snapshot_t(); - } +static Control makeControl(Cont_t cont, MCont_t mcont) { + return Control(cont, mcont); +} + +static Snapshot_t makeSnapshot(Control control) { + // create a snapshot from the current symbolic states and the control + return Snapshot_t(control.cont, control.mcont, SymStack, SymFrames, + SymMemory); } struct Node; @@ -500,6 +535,8 @@ struct NodeBox { explicit NodeBox(NodeBox *parent); std::unique_ptr node; NodeBox *parent; + int cost; + int instr_cost; bool fillIfElseNode(SymVal cond, int id); std::monostate fillFinishedNode(); @@ -508,6 +545,8 @@ struct NodeBox { std::monostate fillSnapshotNode(Snapshot_t snapshot); bool isUnexplored() const; std::vector collect_path_conds(); + int min_cost_of_reaching_here(); + void reach_here(std::function); }; struct Node { @@ -555,10 +594,17 @@ struct IfElseNode : Node { std::unique_ptr true_branch; std::unique_ptr false_branch; int id; + std::optional snapshot; IfElseNode(SymVal cond, NodeBox *parent, int id) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)), id(id) {} + false_branch(std::make_unique(parent)), id(id), + snapshot(std::nullopt) {} + + IfElseNode(SymVal cond, NodeBox *parent, int id, Snapshot_t snapshot) + : cond(cond), true_branch(std::make_unique(parent)), + false_branch(std::make_unique(parent)), id(id), + snapshot(snapshot) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -622,6 +668,7 @@ struct SnapshotNode : Node { SnapshotNode(Snapshot_t snapshot) : snapshot(snapshot) {} std::string to_string() override { return "SnapshotNode"; } const Snapshot_t &get_snapshot() const { return snapshot; } + Snapshot_t move_out_snapshot() { return std::move(snapshot); } protected: void generate_dot(std::ostream &os, int parent_dot_id, @@ -689,11 +736,15 @@ struct Unreachable : Node { inline NodeBox::NodeBox(NodeBox *parent) : node(std::make_unique()), /* TODO: avoid allocation of unexplored node */ - parent(parent) {} + parent(parent), cost(-1), instr_cost(0) {} inline bool NodeBox::fillIfElseNode(SymVal cond, int id) { // fill the current NodeBox with an ifelse branch node when it's unexplored - if (this->isUnexplored()) { + if (auto ptr = dynamic_cast(node.get())) { + node = + std::make_unique(cond, this, id, ptr->move_out_snapshot()); + return true; + } else if (dynamic_cast(node.get())) { node = std::make_unique(cond, this, id); return true; } @@ -738,8 +789,14 @@ inline std::monostate NodeBox::fillUnreachableNode() { } inline bool NodeBox::isUnexplored() const { - return dynamic_cast(node.get()) != nullptr || - dynamic_cast(node.get()) != nullptr; + assert(node != nullptr); + if (dynamic_cast(node.get()) != nullptr) { + return true; + } + if (dynamic_cast(node.get()) != nullptr) { + return true; + } + return false; } inline std::vector NodeBox::collect_path_conds() { @@ -765,6 +822,25 @@ inline std::vector NodeBox::collect_path_conds() { return result; } +inline int NodeBox::min_cost_of_reaching_here() { + if (cost != -1) { + return cost; + } + + if (auto snapshot = dynamic_cast(node.get())) { + cost = snapshot->get_snapshot().cost_of_snapshot(); + return cost; + } + + if (parent != nullptr) { + auto parent_cost = parent->min_cost_of_reaching_here(); + cost = parent_cost + instr_cost; + return cost; + } + cost = instr_cost; + return cost; +} + inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont, SymStack_t stack, SymFrames_t frames, SymMemory_t memory) : stack(std::move(stack)), frames(std::move(frames)), @@ -775,6 +851,12 @@ inline Snapshot_t::Snapshot_t(Cont_t cont, MCont_t mcont, SymStack_t stack, #endif } +inline int Snapshot_t::cost_of_snapshot() { + auto cost_of_stack_copy = SymStack.cost_of_copy(); + auto cost_of_frame_copy = SymFrames.cost_of_copy(); + auto cost_of_memory_copy = SymMemory.cost_of_copy(); + return cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy; +} class ExploreTree_t { public: explicit ExploreTree_t() @@ -813,17 +895,37 @@ class ExploreTree_t { return std::monostate(); } - std::monostate moveCursor(bool branch, Snapshot_t snapshot) { + bool worth_to_create_snapshot() { + // find out the best way to reach the current position via our cost model + auto snapshot_cost = Snapshot_t::cost_of_snapshot(); + auto parent_cost = + cursor->parent ? cursor->parent->min_cost_of_reaching_here() : 0; + auto exec_from_parent_cost = + cursor->min_cost_of_reaching_here() + cursor->instr_cost; + // TODO: return a random result to test the infrastructure, replace this to the + // real cost model later + if (std::rand() % 2 == 0) { + return true; + } else { + return false; + } + } + + std::monostate moveCursor(bool branch, Control control) { Profile.step(StepProfileKind::CURSOR_MOVE); assert(cursor != nullptr); auto if_else_node = dynamic_cast(cursor->node.get()); assert( if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); + int cost_from_parent = CostManager.dump_instr_cost(); if (branch) { true_branch_cov_map[if_else_node->id] = true; if (REUSE_SNAPSHOT) { - if_else_node->false_branch->fillSnapshotNode(snapshot); + if (worth_to_create_snapshot()) { + auto snapshot = makeSnapshot(control); + if_else_node->false_branch->fillSnapshotNode(snapshot); + } } else { // Do nothing, the initial value of the branch is an unexplored node } @@ -831,7 +933,10 @@ class ExploreTree_t { } else { false_branch_cov_map[if_else_node->id] = true; if (REUSE_SNAPSHOT) { - if_else_node->true_branch->fillSnapshotNode(snapshot); + if (worth_to_create_snapshot()) { + auto snapshot = makeSnapshot(control); + if_else_node->true_branch->fillSnapshotNode(snapshot); + } } else { // Do nothing, the initial value of the branch is an unexplored node } @@ -955,6 +1060,41 @@ class SymEnv_t { static SymEnv_t SymEnv; +static std::monostate reset_stacks() { + Stack.reset(); + SymStack.reset(); + Frames.reset(); + SymFrames.reset(); + Memory.reset(); + SymMemory.reset(); + initRand(); + return std::monostate{}; +} + +inline void NodeBox::reach_here(std::function entrypoint) { + // reach the node of exploration tree with given input (symbolic environment) + if (auto snapshot = dynamic_cast(node.get())) { + assert(REUSE_SNAPSHOT); + auto snap = snapshot->get_snapshot(); + snap.resume_execution(this); + } + if (parent == nullptr) { + // if it's the root node, the only way to reach here is to reset everything + // and start a new execution + assert(this == ExploreTree.get_root() && + "Only the root node can have no parent"); + auto timer = ManagedTimer(TimeProfileKind::INSTR); + ExploreTree.reset_cursor(); + reset_stacks(); + entrypoint(); + return; + } + // Reach the parent node, then from the parent node, we can reach here + // TODO: short circuit the lookup + parent->reach_here(entrypoint); + return; +} + struct EvalRes { Num value; int width; // in bits @@ -1072,8 +1212,7 @@ static void resume_conc_states(const SymStack_t &sym_stack, resume_conc_memory(sym_memory, memory, sym_env); } -inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, - NodeBox *node) const { +inline std::monostate Snapshot_t::resume_execution(NodeBox *node) const { // Reset explore tree's cursor ExploreTree.set_cursor(node); @@ -1085,11 +1224,25 @@ inline std::monostate Snapshot_t::resume_execution(SymEnv_t &sym_env, { auto timer = ManagedTimer(TimeProfileKind::RESUME_SNAPSHOT); // Restore the concrete states from the symbolic states - resume_conc_states(stack, frames, memory, Stack, Frames, Memory, sym_env); + resume_conc_states(stack, frames, memory, Stack, Frames, Memory, SymEnv); + } + int sym_size = 0; + { + auto timer = ManagedTimer(TimeProfileKind::COUNT_SYM_SIZE); + for (size_t i = 0; i < stack.size(); ++i) { + sym_size += stack[i].size(); + } + for (size_t i = 0; i < frames.size(); ++i) { + sym_size += frames[i].size(); + } } + std::cout << "[Info] Resumed symbolic execution from snapshot, total " + "symbolic expression and frame size: " + << sym_size << std::endl; + // Resume execution from the continuation auto timer = ManagedTimer(TimeProfileKind::INSTR); return cont(mcont); } -#endif // WASM_SYMBOLIC_RT_HPP \ No newline at end of file +#endif // WASM_SYMBOLIC_RT_HPP diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 739a0f39c..cafddbf0b 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -136,14 +136,20 @@ trait StagedWasmEvaluator extends SAIOps { }) } + trait Control - // TODO: maybe we don't need concern snapshot at compile time at all - trait Snapshot - - // Create a snapshot of the symbolic execution, we should ensure that current symstack is in use + // Save the current control information into a structure Control // We need to store the control information, so we can resume the execution later - def makeSnapshot(kont: Rep[Cont[Unit]], mkont: Rep[MCont[Unit]]): Rep[Snapshot] = { - "snapshot-make".reflectCtrlWith[Snapshot](kont, mkont) + def makeControl(kont: Rep[Cont[Unit]], mkont: Rep[MCont[Unit]]): Rep[Control] = { + "control-make".reflectCtrlWith[Control](kont, mkont) + } + + var instrCost: Int = 0 + + def addInstrCost(): Rep[Unit] = { + "add-instr-cost".reflectCtrlWith[Unit](instrCost) + instrCost = 0 + () } def eval(insts: List[Instr], @@ -152,7 +158,7 @@ trait StagedWasmEvaluator extends SAIOps { trail: Trail[Unit]) (implicit ctx: Context): Rep[Unit] = { if (insts.isEmpty) return kont(ctx)(mkont) - + instrCost += 1 // Predef.println(s"[DEBUG] Evaluating instructions: ${insts.mkString(", ")}") // Predef.println(s"[DEBUG] Current context: $ctx") @@ -352,19 +358,21 @@ trait StagedWasmEvaluator extends SAIOps { eval(els, restK _, mk, restK _ :: trail)(newCtx) }) if (cond.toInt != 0) { - val snapshot = makeSnapshot(elsK, mkont) - ExploreTree.moveCursor(true, snapshot) + val control = makeControl(elsK, mkont) + ExploreTree.moveCursor(true, control) thnK(mkont) } else { - val snapshot = makeSnapshot(thnK, mkont) - ExploreTree.moveCursor(false, snapshot) + val control = makeControl(thnK, mkont) + ExploreTree.moveCursor(false, control) elsK(mkont) } () case Br(label) => info(s"Jump to $label") + addInstrCost() trail(label)(ctx)(mkont) case BrIf(label) => + addInstrCost() val (ty, newCtx) = ctx.pop() val cond = Stack.popC(ty) val symCond = Stack.popS(ty) @@ -379,17 +387,18 @@ trait StagedWasmEvaluator extends SAIOps { }) if (cond.toInt != 0) { info(s"Jump to $label") - val snapshot = makeSnapshot(elsK, mkont) - ExploreTree.moveCursor(true, snapshot) + val control = makeControl(elsK, mkont) + ExploreTree.moveCursor(true, control) thnK(mkont) } else { info(s"Continue") - val snapshot = makeSnapshot(thnK, mkont) - ExploreTree.moveCursor(false, snapshot) + val control = makeControl(thnK, mkont) + ExploreTree.moveCursor(false, control) elsK(mkont) } () case BrTable(labels, default) => + addInstrCost() val (ty, newCtx) = ctx.pop() def aux(choices: List[Int], idx: Int, mkont: Rep[MCont[Unit]]): Rep[Unit] = { if (choices.isEmpty) { @@ -417,13 +426,13 @@ trait StagedWasmEvaluator extends SAIOps { aux(choices.tail, idx + 1, mk) }) if (cond.toInt != 0) { - val snapshot = makeSnapshot(elsK, mkont) - ExploreTree.moveCursor(true, snapshot) + val control = makeControl(elsK, mkont) + ExploreTree.moveCursor(true, control) thnK(mkont) } else { - val snapshot = makeSnapshot(thnK, mkont) - ExploreTree.moveCursor(false, snapshot) + val control = makeControl(thnK, mkont) + ExploreTree.moveCursor(false, control) elsK(mkont) } } @@ -451,6 +460,8 @@ trait StagedWasmEvaluator extends SAIOps { module.funcs(funcIndex) match { case FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) => val locals = bodyLocals ++ ty.inps + instrCost += locals.size * 2 - 1 + addInstrCost() val callee = if (compileCache.contains(funcIndex)) { compileCache(funcIndex) @@ -505,12 +516,14 @@ trait StagedWasmEvaluator extends SAIOps { case Import("console", "log", _) | Import("spectest", "print_i32", _) => //println(s"[DEBUG] current stack: $stack") + addInstrCost() val (ty, newCtx) = ctx.pop() val v = Stack.popC(ty) Stack.popS(ty) println(v.toInt) eval(rest, kont, mkont, trail)(newCtx) case Import("console", "assert", _) => + addInstrCost() val (ty, newCtx) = ctx.pop() val v = Stack.popC(ty) // TODO: We should also add s into exploration tree @@ -858,9 +871,9 @@ trait StagedWasmEvaluator extends SAIOps { "tree-fill-finished".reflectCtrlWith[Unit]() } - def moveCursor(branch: Boolean, snapshot: Rep[Snapshot]): Rep[Unit] = { + def moveCursor(branch: Boolean, control: Rep[Control]): Rep[Unit] = { // when moving cursor from to an unexplored node, we need to change the reuse state - "tree-move-cursor".reflectCtrlWith[Unit](branch, snapshot) + "tree-move-cursor".reflectCtrlWith[Unit](branch, control) } def print(): Rep[Unit] = { @@ -1388,8 +1401,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.pop()") case Node(_, "sym-stack-pop", _, _) => emit("SymStack.pop()") - case Node(_, "snapshot-make", List(k, mk), _) => - emit("makeSnapshot("); shallow(k); emit(", "); shallow(mk); emit(")") + case Node(_, "control-make", List(k, mk), _) => + emit("makeControl("); shallow(k); emit(", "); shallow(mk); emit(")") case Node(_, "frame-pop", List(i), _) => emit("Frames.popFrame("); shallow(i); emit(")") case Node(_, "sym-frame-pop", List(i), _) => @@ -1511,6 +1524,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b, snapshot), _) => emit("ExploreTree.moveCursor("); shallow(b); emit(", "); shallow(snapshot); emit(")") + case Node(_, "add-instr-cost", List(n), _) => + emit("CostManager.add_instr_cost("); shallow(n); emit(")") case Node(_, "tree-print", List(), _) => emit("ExploreTree.print()") case Node(_, "tree-dump-graphviz", List(f), _) => From a1501030b56be67d3329b0516b4500d1f7dc4de3 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 18 Oct 2025 20:59:19 +0800 Subject: [PATCH 053/105] a cost model to determin if we want to create snapshot --- benchmarks/wasm/compare_wasp/Makefile | 10 ++++-- headers/wasm/config.hpp | 6 ++++ headers/wasm/profile.hpp | 4 +++ headers/wasm/symbolic_rt.hpp | 46 ++++++++++++++------------- 4 files changed, 41 insertions(+), 25 deletions(-) diff --git a/benchmarks/wasm/compare_wasp/Makefile b/benchmarks/wasm/compare_wasp/Makefile index c9cc74ae1..1c3e58c69 100644 --- a/benchmarks/wasm/compare_wasp/Makefile +++ b/benchmarks/wasm/compare_wasp/Makefile @@ -1,12 +1,16 @@ .PHONY: all run clean -all: large-branch.wat.cpp.imm.noreuse.exe large-branch.wat.cpp.imm.exe +all: large-branch.wat.cpp.imm.noreuse.exe large-branch.wat.cpp.imm.exe large-branch.wat.cpp.imm.cost-model.exe large-branch.wat.cpp.imm.noreuse.exe: large-branch.wat.cpp - g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.noreuse.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 -DNO_REUSE + g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.noreuse.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 -DNO_REUSE -DENABLE_PROFILE_STEP large-branch.wat.cpp.imm.exe: large-branch.wat.cpp - g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 + g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 -DENABLE_PROFILE_STEP + +large-branch.wat.cpp.imm.cost-model.exe: large-branch.wat.cpp + g++ large-branch.wat.cpp -o large-branch.wat.cpp.imm.cost-model.exe -DUSE_IMM -I ../../../headers -lz3 -DENABLE_PROFILE_TIME -O3 -DUSE_COST_MODEL + run: all ./large-branch.wat.cpp.imm.noreuse.exe diff --git a/headers/wasm/config.hpp b/headers/wasm/config.hpp index a9c8d5a12..037c62634 100644 --- a/headers/wasm/config.hpp +++ b/headers/wasm/config.hpp @@ -55,4 +55,10 @@ static const bool INTERACTIVE_MODE = true; static const bool INTERACTIVE_MODE = false; #endif +#ifdef USE_COST_MODEL +static const bool ENABLE_COST_MODEL = true; +#else +static const bool ENABLE_COST_MODEL = false; +#endif + #endif // CONFIG_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index bc4ce911d..9814b5eb5 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -20,6 +20,7 @@ enum class StepProfileKind { CURSOR_MOVE, MEM_GROW, SNAPSHOT_CREATE, + SYM_EVAL, OperationCount // keep this as the last element, this is used to get the // number of kinds of operations }; @@ -87,6 +88,9 @@ class Profile_t { << op_count[static_cast( StepProfileKind::SNAPSHOT_CREATE)] << std::endl; + std::cout << "Total SYM_EVAL operations: " + << op_count[static_cast(StepProfileKind::SYM_EVAL)] + << std::endl; std::cout << "Total time for instruction execution (s): " << std::setprecision(15) << execution_time << std::endl; } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 1423dcf16..6edef6ee8 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -855,7 +855,8 @@ inline int Snapshot_t::cost_of_snapshot() { auto cost_of_stack_copy = SymStack.cost_of_copy(); auto cost_of_frame_copy = SymFrames.cost_of_copy(); auto cost_of_memory_copy = SymMemory.cost_of_copy(); - return cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy; + return 5.336 * + (cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy); } class ExploreTree_t { public: @@ -896,19 +897,23 @@ class ExploreTree_t { } bool worth_to_create_snapshot() { + if (!ENABLE_COST_MODEL) { + return REUSE_SNAPSHOT; + } // find out the best way to reach the current position via our cost model auto snapshot_cost = Snapshot_t::cost_of_snapshot(); - auto parent_cost = - cursor->parent ? cursor->parent->min_cost_of_reaching_here() : 0; - auto exec_from_parent_cost = - cursor->min_cost_of_reaching_here() + cursor->instr_cost; - // TODO: return a random result to test the infrastructure, replace this to the - // real cost model later - if (std::rand() % 2 == 0) { - return true; + int reach_parent_cost = 0; + if (cursor->parent) { + reach_parent_cost = cursor->parent->min_cost_of_reaching_here(); } else { - return false; + reach_parent_cost = 0; } + auto parent_cost = + cursor->parent ? cursor->parent->min_cost_of_reaching_here() : 0; + auto exec_from_parent_cost = reach_parent_cost + cursor->instr_cost; + GENSYM_INFO("The score of snapshot tendency: " + std::to_string(exec_from_parent_cost - + snapshot_cost)); + return snapshot_cost <= exec_from_parent_cost; } std::monostate moveCursor(bool branch, Control control) { @@ -921,22 +926,18 @@ class ExploreTree_t { int cost_from_parent = CostManager.dump_instr_cost(); if (branch) { true_branch_cov_map[if_else_node->id] = true; - if (REUSE_SNAPSHOT) { - if (worth_to_create_snapshot()) { - auto snapshot = makeSnapshot(control); - if_else_node->false_branch->fillSnapshotNode(snapshot); - } + if (worth_to_create_snapshot()) { + auto snapshot = makeSnapshot(control); + if_else_node->false_branch->fillSnapshotNode(snapshot); } else { // Do nothing, the initial value of the branch is an unexplored node } cursor = if_else_node->true_branch.get(); } else { false_branch_cov_map[if_else_node->id] = true; - if (REUSE_SNAPSHOT) { - if (worth_to_create_snapshot()) { - auto snapshot = makeSnapshot(control); - if_else_node->true_branch->fillSnapshotNode(snapshot); - } + if (worth_to_create_snapshot()) { + auto snapshot = makeSnapshot(control); + if_else_node->true_branch->fillSnapshotNode(snapshot); } else { // Do nothing, the initial value of the branch is an unexplored node } @@ -1077,8 +1078,8 @@ inline void NodeBox::reach_here(std::function entrypoint) { assert(REUSE_SNAPSHOT); auto snap = snapshot->get_snapshot(); snap.resume_execution(this); - } - if (parent == nullptr) { + return; + } else if (parent == nullptr) { // if it's the root node, the only way to reach here is to reset everything // and start a new execution assert(this == ExploreTree.get_root() && @@ -1104,6 +1105,7 @@ struct EvalRes { // TODO: reduce the re-computation of the same symbolic expression, it's better // if it can be done by the smt solver static EvalRes eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { + Profile.step(StepProfileKind::SYM_EVAL); assert(sym.symptr != nullptr && "Symbolic expression is null"); if (auto concrete = dynamic_cast(sym.symptr.get())) { return EvalRes(concrete->value, 32); From 2ad0949337f8c8c2fcd3e9e96da50c9700854680 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 20:31:18 -0400 Subject: [PATCH 054/105] update btree benchmarks --- benchmarks/pldi2026/btree/2o1u.wast | 3655 +++++++++++++++ benchmarks/pldi2026/btree/2o2u.wast | 3694 +++++++++++++++ benchmarks/pldi2026/btree/2o3u.wast | 3740 +++++++++++++++ benchmarks/pldi2026/btree/3o1u.wast | 3698 +++++++++++++++ benchmarks/pldi2026/btree/3o2u.wast | 3744 +++++++++++++++ benchmarks/pldi2026/btree/3o3u.wast | 3795 +++++++++++++++ benchmarks/pldi2026/btree/4o1u.wast | 3747 +++++++++++++++ benchmarks/pldi2026/btree/4o2u.wast | 3798 +++++++++++++++ benchmarks/pldi2026/btree/4o3u.wast | 3854 +++++++++++++++ benchmarks/pldi2026/btree/5o1u.wast | 3801 +++++++++++++++ benchmarks/pldi2026/btree/5o2u.wast | 3858 +++++++++++++++ benchmarks/pldi2026/btree/5o3u.wast | 3915 ++++++++++++++++ benchmarks/pldi2026/btree/6o1u.wast | 3861 +++++++++++++++ benchmarks/pldi2026/btree/6o2u.wast | 3922 ++++++++++++++++ benchmarks/pldi2026/btree/6o3u.wast | 3987 ++++++++++++++++ benchmarks/pldi2026/btree/7o1u.wast | 3926 ++++++++++++++++ benchmarks/pldi2026/btree/7o2u.wast | 3992 ++++++++++++++++ benchmarks/pldi2026/btree/7o3u.wast | 4065 ++++++++++++++++ benchmarks/pldi2026/btree/8o1u.wast | 3996 ++++++++++++++++ benchmarks/pldi2026/btree/8o2u.wast | 4059 ++++++++++++++++ benchmarks/pldi2026/btree/9o1u.wast | 4072 ++++++++++++++++ benchmarks/pldi2026/btree/9o2u.wast | 4147 +++++++++++++++++ .../wasm/btree/2o1u-unlabeled.wat copy.cpp | 71 + benchmarks/wasm/btree/Makefile | 53 + 24 files changed, 85450 insertions(+) create mode 100644 benchmarks/pldi2026/btree/2o1u.wast create mode 100644 benchmarks/pldi2026/btree/2o2u.wast create mode 100644 benchmarks/pldi2026/btree/2o3u.wast create mode 100644 benchmarks/pldi2026/btree/3o1u.wast create mode 100644 benchmarks/pldi2026/btree/3o2u.wast create mode 100644 benchmarks/pldi2026/btree/3o3u.wast create mode 100644 benchmarks/pldi2026/btree/4o1u.wast create mode 100644 benchmarks/pldi2026/btree/4o2u.wast create mode 100644 benchmarks/pldi2026/btree/4o3u.wast create mode 100644 benchmarks/pldi2026/btree/5o1u.wast create mode 100644 benchmarks/pldi2026/btree/5o2u.wast create mode 100644 benchmarks/pldi2026/btree/5o3u.wast create mode 100644 benchmarks/pldi2026/btree/6o1u.wast create mode 100644 benchmarks/pldi2026/btree/6o2u.wast create mode 100644 benchmarks/pldi2026/btree/6o3u.wast create mode 100644 benchmarks/pldi2026/btree/7o1u.wast create mode 100644 benchmarks/pldi2026/btree/7o2u.wast create mode 100644 benchmarks/pldi2026/btree/7o3u.wast create mode 100644 benchmarks/pldi2026/btree/8o1u.wast create mode 100644 benchmarks/pldi2026/btree/8o2u.wast create mode 100644 benchmarks/pldi2026/btree/9o1u.wast create mode 100644 benchmarks/pldi2026/btree/9o2u.wast create mode 100644 benchmarks/wasm/btree/2o1u-unlabeled.wat copy.cpp create mode 100644 benchmarks/wasm/btree/Makefile diff --git a/benchmarks/pldi2026/btree/2o1u.wast b/benchmarks/pldi2026/btree/2o1u.wast new file mode 100644 index 000000000..b9384f568 --- /dev/null +++ b/benchmarks/pldi2026/btree/2o1u.wast @@ -0,0 +1,3655 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (print_stack) + (i32.const -1) + (i32.eq) + (print_stack) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (print_stack) + (i32.const -1) + (i32.eq) + (print_stack) + + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00")) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/2o2u.wast b/benchmarks/pldi2026/btree/2o2u.wast new file mode 100644 index 000000000..384e4feee --- /dev/null +++ b/benchmarks/pldi2026/btree/2o2u.wast @@ -0,0 +1,3694 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + ;; i + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00i\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/2o3u.wast b/benchmarks/pldi2026/btree/2o3u.wast new file mode 100644 index 000000000..090f36e0f --- /dev/null +++ b/benchmarks/pldi2026/btree/2o3u.wast @@ -0,0 +1,3740 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + ;; i + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/3o1u.wast b/benchmarks/pldi2026/btree/3o1u.wast new file mode 100644 index 000000000..ef2c9309a --- /dev/null +++ b/benchmarks/pldi2026/btree/3o1u.wast @@ -0,0 +1,3698 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/3o2u.wast b/benchmarks/pldi2026/btree/3o2u.wast new file mode 100644 index 000000000..ffa990f10 --- /dev/null +++ b/benchmarks/pldi2026/btree/3o2u.wast @@ -0,0 +1,3744 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + ;; i + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/3o3u.wast b/benchmarks/pldi2026/btree/3o3u.wast new file mode 100644 index 000000000..0c191307c --- /dev/null +++ b/benchmarks/pldi2026/btree/3o3u.wast @@ -0,0 +1,3795 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + ;; i + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/4o1u.wast b/benchmarks/pldi2026/btree/4o1u.wast new file mode 100644 index 000000000..da4203391 --- /dev/null +++ b/benchmarks/pldi2026/btree/4o1u.wast @@ -0,0 +1,3747 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/4o2u.wast b/benchmarks/pldi2026/btree/4o2u.wast new file mode 100644 index 000000000..7b3c6eecf --- /dev/null +++ b/benchmarks/pldi2026/btree/4o2u.wast @@ -0,0 +1,3798 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + ;; i + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/4o3u.wast b/benchmarks/pldi2026/btree/4o3u.wast new file mode 100644 index 000000000..30faaedda --- /dev/null +++ b/benchmarks/pldi2026/btree/4o3u.wast @@ -0,0 +1,3854 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + ;; i + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/5o1u.wast b/benchmarks/pldi2026/btree/5o1u.wast new file mode 100644 index 000000000..9c6338700 --- /dev/null +++ b/benchmarks/pldi2026/btree/5o1u.wast @@ -0,0 +1,3801 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/5o2u.wast b/benchmarks/pldi2026/btree/5o2u.wast new file mode 100644 index 000000000..cb2a650f1 --- /dev/null +++ b/benchmarks/pldi2026/btree/5o2u.wast @@ -0,0 +1,3858 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + ;; i + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/5o3u.wast b/benchmarks/pldi2026/btree/5o3u.wast new file mode 100644 index 000000000..6342b1a5d --- /dev/null +++ b/benchmarks/pldi2026/btree/5o3u.wast @@ -0,0 +1,3915 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + ;; i + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; j + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/6o1u.wast b/benchmarks/pldi2026/btree/6o1u.wast new file mode 100644 index 000000000..ccc8520f0 --- /dev/null +++ b/benchmarks/pldi2026/btree/6o1u.wast @@ -0,0 +1,3861 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/6o2u.wast b/benchmarks/pldi2026/btree/6o2u.wast new file mode 100644 index 000000000..9038d51ee --- /dev/null +++ b/benchmarks/pldi2026/btree/6o2u.wast @@ -0,0 +1,3922 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + ;; i + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/6o3u.wast b/benchmarks/pldi2026/btree/6o3u.wast new file mode 100644 index 000000000..153c95b7a --- /dev/null +++ b/benchmarks/pldi2026/btree/6o3u.wast @@ -0,0 +1,3987 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + ;; i + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/7o1u.wast b/benchmarks/pldi2026/btree/7o1u.wast new file mode 100644 index 000000000..69e17d056 --- /dev/null +++ b/benchmarks/pldi2026/btree/7o1u.wast @@ -0,0 +1,3926 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/7o2u.wast b/benchmarks/pldi2026/btree/7o2u.wast new file mode 100644 index 000000000..7c5b411a1 --- /dev/null +++ b/benchmarks/pldi2026/btree/7o2u.wast @@ -0,0 +1,3992 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/7o3u.wast b/benchmarks/pldi2026/btree/7o3u.wast new file mode 100644 index 000000000..c51d9b646 --- /dev/null +++ b/benchmarks/pldi2026/btree/7o3u.wast @@ -0,0 +1,4065 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; i + (i32.const 1042) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/8o1u.wast b/benchmarks/pldi2026/btree/8o1u.wast new file mode 100644 index 000000000..3c9425018 --- /dev/null +++ b/benchmarks/pldi2026/btree/8o1u.wast @@ -0,0 +1,3996 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/8o2u.wast b/benchmarks/pldi2026/btree/8o2u.wast new file mode 100644 index 000000000..9d19d9f7e --- /dev/null +++ b/benchmarks/pldi2026/btree/8o2u.wast @@ -0,0 +1,4059 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (sym_int32 "a") + (sym_int32 "b") + (i32.ne) + + ;;c + (sym_int32 "c") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (sym_int32 "d") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (sym_int32 "e") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (sym_int32 "f") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (sym_int32 "g") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (sym_int32 "x") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (sym_int32 "h") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + ;; i + (sym_int32 "i") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/9o1u.wast b/benchmarks/pldi2026/btree/9o1u.wast new file mode 100644 index 000000000..ef8a94483 --- /dev/null +++ b/benchmarks/pldi2026/btree/9o1u.wast @@ -0,0 +1,4072 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; y + (i32.const 1046) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "x") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x>y + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + (get_sym_int32 "x") + (get_sym_int32 "y") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "y") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "y") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; y + (local.get 0) + (get_sym_int32 "y") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/btree/9o2u.wast b/benchmarks/pldi2026/btree/9o2u.wast new file mode 100644 index 000000000..88a7615ab --- /dev/null +++ b/benchmarks/pldi2026/btree/9o2u.wast @@ -0,0 +1,4147 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 9 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; y + (i32.const 1046) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "x") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x>y + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + (get_sym_int32 "x") + (get_sym_int32 "y") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "y") + (i32.ne) + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "y") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "y") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; y + (local.get 0) + (get_sym_int32 "y") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") +) +(invoke "main") diff --git a/benchmarks/wasm/btree/2o1u-unlabeled.wat copy.cpp b/benchmarks/wasm/btree/2o1u-unlabeled.wat copy.cpp new file mode 100644 index 000000000..a449fd2a4 --- /dev/null +++ b/benchmarks/wasm/btree/2o1u-unlabeled.wat copy.cpp @@ -0,0 +1,71 @@ +std::monostate Snippet(std::monostate x0) { +Globals.pushFrame(0); +SymGlobals.pushFrame(0); +Frames.pushFrame(0); +SymFrames.pushFrame(0); +Stack.push(I32V(2)); +SymStack.push(Concrete(I32V(2))); +Stack.pop(); +SymVal x3 = SymStack.pop(); +SymVal x4 = x3.makeSymbolic(); +Stack.push(SymEnv.read(x4)); +SymStack.push(x4); +Stack.push(I32V(1)); +SymStack.push(Concrete(I32V(1))); +Stack.pop(); +SymVal x5 = SymStack.pop(); +SymVal x6 = x5.makeSymbolic(); +Stack.push(SymEnv.read(x6)); +SymStack.push(x6); +Stack.push(I32V(0)); +SymStack.push(Concrete(I32V(0))); +Stack.pop(); +SymVal x7 = SymStack.pop(); +SymVal x8 = x7.makeSymbolic(); +Stack.push(SymEnv.read(x8)); +SymStack.push(x8); +CostManager.add_instr_cost(14); +info("Exiting the function at 5, stackSize =", Stack.size()); +Frames.popFrame(6); +SymFrames.popFrame(6); +Num x5014 = Stack.peek(); +SymVal x5015 = SymStack.peek(); +Frames.set(3, x5014); +SymFrames.set(3, x5015); +Stack.push(Frames.get(1)); +SymStack.push(SymFrames.get(1)); +CostManager.add_instr_cost(8); +Stack.pop(); +Stack.pop(); +SymStack.pop(); +SymStack.pop(); +std::monostate x5032 = std::monostate(); +std::function x5033; +x5033 = [=](std::monostate x5034)->std::monostate { +std::monostate(); +return x5018(x5035); +}; +Num x5180 = Stack.pop(); +Num x5181 = Stack.pop(); +Num x5182 = Stack.pop(); +SymVal x5183 = SymStack.pop(); +SymVal x5184 = SymStack.pop(); +SymVal x5185 = SymStack.pop(); +std::monostate x5190 = std::monostate(); +std::function x5191; +x5191 = [=](std::monostate x5192)->std::monostate { +std::monostate(); +return x5188(x1); +}; +Frames.pushFrame(4); +SymFrames.pushFrame(4); +Frames.set(0, x5182); +Frames.set(1, x5181); +Frames.set(2, x5180); +SymFrames.set(0, x5185); +SymFrames.set(1, x5184); +SymFrames.set(2, x5183); +x5153(x5191); +Frames.popFrame(0); +return SymFrames.popFrame(0); +} \ No newline at end of file diff --git a/benchmarks/wasm/btree/Makefile b/benchmarks/wasm/btree/Makefile new file mode 100644 index 000000000..a876c01d9 --- /dev/null +++ b/benchmarks/wasm/btree/Makefile @@ -0,0 +1,53 @@ +# Makefile for building different versions of 2o1u-unlabeled.wat.cpp + +CXX := g++ +SRC := 2o1u-unlabeled.wat.cpp +HEADERS := ../../headers/ +LDFLAGS := -lz3 +CXXFLAGS := -g -I $(HEADERS) -std=c++17 -DENABLE_PROFILE -fno-omit-frame-pointer -O3 -DENABLE_PROFILE_TIME + +.PHONY: all clean benchmark + +all: 2o1u-unlabeled.wat.cpp.imm.no-snap.exe 2o1u-unlabeled.wat.cpp.imm.exe 2o1u-unlabeled.wat.cpp.no-snap.exe 2o1u-unlabeled.wat.cpp.exe \ + 2o1u-unlabeled.wat.cpp.concolic.imm.no-snap.exe 2o1u-unlabeled.wat.cpp.concolic.imm.exe 2o1u-unlabeled.wat.cpp.concolic.no-snap.exe 2o1u-unlabeled.wat.cpp.concolic.exe 2o1u-unlabeled.wat.cpp.concolic.imm.cost-model.exe + +2o1u-unlabeled.wat.cpp.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DRUN_ONCE + +2o1u-unlabeled.wat.cpp.no-snap.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DNO_REUSE -DRUN_ONCE + +2o1u-unlabeled.wat.cpp.imm.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DUSE_IMM -DRUN_ONCE + +2o1u-unlabeled.wat.cpp.imm.no-snap.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DUSE_IMM -DNO_REUSE -DRUN_ONCE + + +## Concolic execution tests +2o1u-unlabeled.wat.cpp.concolic.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DBY_COVERAGE + +2o1u-unlabeled.wat.cpp.concolic.no-snap.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DNO_REUSE -DBY_COVERAGE + +2o1u-unlabeled.wat.cpp.concolic.imm.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DUSE_IMM -DBY_COVERAGE + +2o1u-unlabeled.wat.cpp.concolic.imm.no-snap.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DUSE_IMM -DNO_REUSE -DBY_COVERAGE + +2o1u-unlabeled.wat.cpp.concolic.imm.cost-model.exe: $(SRC) + $(CXX) $< -o $@ $(CXXFLAGS) $(LDFLAGS) -DUSE_IMM -DNO_REUSE -DBY_COVERAGE -DUSE_COST_MODEL + +benchmark: all + hyperfine './2o1u-unlabeled.wat.cpp.imm.no-snap.exe' \ + './2o1u-unlabeled.wat.cpp.imm.exe' \ + './2o1u-unlabeled.wat.cpp.no-snap.exe' \ + './2o1u-unlabeled.wat.cpp.exe' + hyperfine './2o1u-unlabeled.wat.cpp.concolic.imm.no-snap.exe' \ + './2o1u-unlabeled.wat.cpp.concolic.imm.exe' \ + './2o1u-unlabeled.wat.cpp.concolic.no-snap.exe' \ + './2o1u-unlabeled.wat.cpp.concolic.exe' +clean: + rm -f *.exe From a3ad84f32595a3d1d438de93e01cbbe38dc6232b Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:10:40 -0400 Subject: [PATCH 055/105] rename --- .../pldi2026/btree/{2o1u.wast => 2o1u.wat} | 80 ++++++++++++------- .../pldi2026/btree/{2o2u.wast => 2o2u.wat} | 0 .../pldi2026/btree/{2o3u.wast => 2o3u.wat} | 0 .../pldi2026/btree/{3o1u.wast => 3o1u.wat} | 0 .../pldi2026/btree/{3o2u.wast => 3o2u.wat} | 0 .../pldi2026/btree/{3o3u.wast => 3o3u.wat} | 0 .../pldi2026/btree/{4o1u.wast => 4o1u.wat} | 0 .../pldi2026/btree/{4o2u.wast => 4o2u.wat} | 0 .../pldi2026/btree/{4o3u.wast => 4o3u.wat} | 0 .../pldi2026/btree/{5o1u.wast => 5o1u.wat} | 0 .../pldi2026/btree/{5o2u.wast => 5o2u.wat} | 0 .../pldi2026/btree/{5o3u.wast => 5o3u.wat} | 0 .../pldi2026/btree/{6o1u.wast => 6o1u.wat} | 0 .../pldi2026/btree/{6o2u.wast => 6o2u.wat} | 0 .../pldi2026/btree/{6o3u.wast => 6o3u.wat} | 0 .../pldi2026/btree/{7o1u.wast => 7o1u.wat} | 0 .../pldi2026/btree/{7o2u.wast => 7o2u.wat} | 0 .../pldi2026/btree/{7o3u.wast => 7o3u.wat} | 0 .../pldi2026/btree/{8o1u.wast => 8o1u.wat} | 0 .../pldi2026/btree/{8o2u.wast => 8o2u.wat} | 0 .../pldi2026/btree/{9o1u.wast => 9o1u.wat} | 0 .../pldi2026/btree/{9o2u.wast => 9o2u.wat} | 0 22 files changed, 51 insertions(+), 29 deletions(-) rename benchmarks/pldi2026/btree/{2o1u.wast => 2o1u.wat} (98%) rename benchmarks/pldi2026/btree/{2o2u.wast => 2o2u.wat} (100%) rename benchmarks/pldi2026/btree/{2o3u.wast => 2o3u.wat} (100%) rename benchmarks/pldi2026/btree/{3o1u.wast => 3o1u.wat} (100%) rename benchmarks/pldi2026/btree/{3o2u.wast => 3o2u.wat} (100%) rename benchmarks/pldi2026/btree/{3o3u.wast => 3o3u.wat} (100%) rename benchmarks/pldi2026/btree/{4o1u.wast => 4o1u.wat} (100%) rename benchmarks/pldi2026/btree/{4o2u.wast => 4o2u.wat} (100%) rename benchmarks/pldi2026/btree/{4o3u.wast => 4o3u.wat} (100%) rename benchmarks/pldi2026/btree/{5o1u.wast => 5o1u.wat} (100%) rename benchmarks/pldi2026/btree/{5o2u.wast => 5o2u.wat} (100%) rename benchmarks/pldi2026/btree/{5o3u.wast => 5o3u.wat} (100%) rename benchmarks/pldi2026/btree/{6o1u.wast => 6o1u.wat} (100%) rename benchmarks/pldi2026/btree/{6o2u.wast => 6o2u.wat} (100%) rename benchmarks/pldi2026/btree/{6o3u.wast => 6o3u.wat} (100%) rename benchmarks/pldi2026/btree/{7o1u.wast => 7o1u.wat} (100%) rename benchmarks/pldi2026/btree/{7o2u.wast => 7o2u.wat} (100%) rename benchmarks/pldi2026/btree/{7o3u.wast => 7o3u.wat} (100%) rename benchmarks/pldi2026/btree/{8o1u.wast => 8o1u.wat} (100%) rename benchmarks/pldi2026/btree/{8o2u.wast => 8o2u.wat} (100%) rename benchmarks/pldi2026/btree/{9o1u.wast => 9o1u.wat} (100%) rename benchmarks/pldi2026/btree/{9o2u.wast => 9o2u.wat} (100%) diff --git a/benchmarks/pldi2026/btree/2o1u.wast b/benchmarks/pldi2026/btree/2o1u.wat similarity index 98% rename from benchmarks/pldi2026/btree/2o1u.wast rename to benchmarks/pldi2026/btree/2o1u.wat index b9384f568..d57fe9d25 100644 --- a/benchmarks/pldi2026/btree/2o1u.wast +++ b/benchmarks/pldi2026/btree/2o1u.wat @@ -1,7 +1,15 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) + (memory $0 1) - + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree (i32.const 0) (local.get 0) @@ -3548,14 +3556,16 @@ ;; 2 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) - (i32.ne) + (call $i32.symbolic) + (i32.ne) ;; logical order: a>b - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) (i32.and) @@ -3563,46 +3573,55 @@ ;; 1 symbolic variable w/o order ;; h (i32.const 1028) - (i32.symbolic) - (get_sym_int32 "a") + (call $i32.symbolic) + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3613,43 +3632,46 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) - (print_stack) + ;; (print_stack) (i32.const -1) (i32.eq) - (print_stack) + ;; (print_stack) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) - (print_stack) + ;; (print_stack) (i32.const -1) (i32.eq) - (print_stack) + ;; (print_stack) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00h\00")) -(invoke "main") diff --git a/benchmarks/pldi2026/btree/2o2u.wast b/benchmarks/pldi2026/btree/2o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/2o2u.wast rename to benchmarks/pldi2026/btree/2o2u.wat diff --git a/benchmarks/pldi2026/btree/2o3u.wast b/benchmarks/pldi2026/btree/2o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/2o3u.wast rename to benchmarks/pldi2026/btree/2o3u.wat diff --git a/benchmarks/pldi2026/btree/3o1u.wast b/benchmarks/pldi2026/btree/3o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/3o1u.wast rename to benchmarks/pldi2026/btree/3o1u.wat diff --git a/benchmarks/pldi2026/btree/3o2u.wast b/benchmarks/pldi2026/btree/3o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/3o2u.wast rename to benchmarks/pldi2026/btree/3o2u.wat diff --git a/benchmarks/pldi2026/btree/3o3u.wast b/benchmarks/pldi2026/btree/3o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/3o3u.wast rename to benchmarks/pldi2026/btree/3o3u.wat diff --git a/benchmarks/pldi2026/btree/4o1u.wast b/benchmarks/pldi2026/btree/4o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/4o1u.wast rename to benchmarks/pldi2026/btree/4o1u.wat diff --git a/benchmarks/pldi2026/btree/4o2u.wast b/benchmarks/pldi2026/btree/4o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/4o2u.wast rename to benchmarks/pldi2026/btree/4o2u.wat diff --git a/benchmarks/pldi2026/btree/4o3u.wast b/benchmarks/pldi2026/btree/4o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/4o3u.wast rename to benchmarks/pldi2026/btree/4o3u.wat diff --git a/benchmarks/pldi2026/btree/5o1u.wast b/benchmarks/pldi2026/btree/5o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/5o1u.wast rename to benchmarks/pldi2026/btree/5o1u.wat diff --git a/benchmarks/pldi2026/btree/5o2u.wast b/benchmarks/pldi2026/btree/5o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/5o2u.wast rename to benchmarks/pldi2026/btree/5o2u.wat diff --git a/benchmarks/pldi2026/btree/5o3u.wast b/benchmarks/pldi2026/btree/5o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/5o3u.wast rename to benchmarks/pldi2026/btree/5o3u.wat diff --git a/benchmarks/pldi2026/btree/6o1u.wast b/benchmarks/pldi2026/btree/6o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/6o1u.wast rename to benchmarks/pldi2026/btree/6o1u.wat diff --git a/benchmarks/pldi2026/btree/6o2u.wast b/benchmarks/pldi2026/btree/6o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/6o2u.wast rename to benchmarks/pldi2026/btree/6o2u.wat diff --git a/benchmarks/pldi2026/btree/6o3u.wast b/benchmarks/pldi2026/btree/6o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/6o3u.wast rename to benchmarks/pldi2026/btree/6o3u.wat diff --git a/benchmarks/pldi2026/btree/7o1u.wast b/benchmarks/pldi2026/btree/7o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/7o1u.wast rename to benchmarks/pldi2026/btree/7o1u.wat diff --git a/benchmarks/pldi2026/btree/7o2u.wast b/benchmarks/pldi2026/btree/7o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/7o2u.wast rename to benchmarks/pldi2026/btree/7o2u.wat diff --git a/benchmarks/pldi2026/btree/7o3u.wast b/benchmarks/pldi2026/btree/7o3u.wat similarity index 100% rename from benchmarks/pldi2026/btree/7o3u.wast rename to benchmarks/pldi2026/btree/7o3u.wat diff --git a/benchmarks/pldi2026/btree/8o1u.wast b/benchmarks/pldi2026/btree/8o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/8o1u.wast rename to benchmarks/pldi2026/btree/8o1u.wat diff --git a/benchmarks/pldi2026/btree/8o2u.wast b/benchmarks/pldi2026/btree/8o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/8o2u.wast rename to benchmarks/pldi2026/btree/8o2u.wat diff --git a/benchmarks/pldi2026/btree/9o1u.wast b/benchmarks/pldi2026/btree/9o1u.wat similarity index 100% rename from benchmarks/pldi2026/btree/9o1u.wast rename to benchmarks/pldi2026/btree/9o1u.wat diff --git a/benchmarks/pldi2026/btree/9o2u.wast b/benchmarks/pldi2026/btree/9o2u.wat similarity index 100% rename from benchmarks/pldi2026/btree/9o2u.wast rename to benchmarks/pldi2026/btree/9o2u.wat From 8a8d6d02d6699b23d88ed4f18fa1abc0b7e3a4cb Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:12:23 -0400 Subject: [PATCH 056/105] turn wast to wat --- benchmarks/pldi2026/btree/2o2u.wat | 2 +- benchmarks/pldi2026/btree/2o3u.wat | 2 +- benchmarks/pldi2026/btree/3o1u.wat | 2 +- benchmarks/pldi2026/btree/3o2u.wat | 2 +- benchmarks/pldi2026/btree/3o3u.wat | 2 +- benchmarks/pldi2026/btree/4o1u.wat | 2 +- benchmarks/pldi2026/btree/4o2u.wat | 2 +- benchmarks/pldi2026/btree/4o3u.wat | 2 +- benchmarks/pldi2026/btree/5o1u.wat | 2 +- benchmarks/pldi2026/btree/5o2u.wat | 2 +- benchmarks/pldi2026/btree/5o3u.wat | 2 +- benchmarks/pldi2026/btree/6o1u.wat | 2 +- benchmarks/pldi2026/btree/6o2u.wat | 2 +- benchmarks/pldi2026/btree/6o3u.wat | 2 +- benchmarks/pldi2026/btree/7o1u.wat | 2 +- benchmarks/pldi2026/btree/7o2u.wat | 2 +- benchmarks/pldi2026/btree/7o3u.wat | 2 +- benchmarks/pldi2026/btree/8o1u.wat | 2 +- benchmarks/pldi2026/btree/8o2u.wat | 2 +- benchmarks/pldi2026/btree/9o1u.wat | 2 +- benchmarks/pldi2026/btree/9o2u.wat | 2 +- 21 files changed, 21 insertions(+), 21 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 384e4feee..d5172a5e5 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3691,4 +3691,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00h\00i\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index 090f36e0f..2d0a90aec 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3737,4 +3737,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index ef2c9309a..b9d56a090 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3695,4 +3695,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index ffa990f10..17824b8c2 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3741,4 +3741,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 0c191307c..01e18274f 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3792,4 +3792,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index da4203391..0a929b47f 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3744,4 +3744,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 7b3c6eecf..e7c20f49a 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3795,4 +3795,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 30faaedda..8008797dc 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3851,4 +3851,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 9c6338700..44eb94481 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3798,4 +3798,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index cb2a650f1..961fe3dd8 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3855,4 +3855,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 6342b1a5d..02a3a0e95 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3912,4 +3912,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index ccc8520f0..8d609fbae 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3858,4 +3858,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 9038d51ee..33292ec48 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3919,4 +3919,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 153c95b7a..24fe6fd10 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3984,4 +3984,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 69e17d056..bfa1a2b15 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3923,4 +3923,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 7c5b411a1..1b9fee44a 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3989,4 +3989,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index c51d9b646..783374a18 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -4062,4 +4062,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 3c9425018..9fb9a51ab 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3993,4 +3993,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index 9d19d9f7e..be3cc6b68 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -4056,4 +4056,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index ef8a94483..73f3820f0 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -4069,4 +4069,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") ) -(invoke "main") + diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 88a7615ab..3ecf8dbf2 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -4144,4 +4144,4 @@ (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") ) -(invoke "main") + From ea0510127a93fa0f8fa061ef21edb7e8d49a5d1c Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:16:30 -0400 Subject: [PATCH 057/105] use imported api for symbolic operations so they can be run by wat2wasm currently only 2o2u.wat works --- benchmarks/pldi2026/btree/2o2u.wat | 7 + benchmarks/pldi2026/btree/2o3u.wat | 7 + benchmarks/pldi2026/btree/3o1u.wat | 7 + benchmarks/pldi2026/btree/3o2u.wat | 7 + benchmarks/pldi2026/btree/3o3u.wat | 7 + benchmarks/pldi2026/btree/4o1u.wat | 7 + benchmarks/pldi2026/btree/4o2u.wat | 7 + benchmarks/pldi2026/btree/4o3u.wat | 7 + benchmarks/pldi2026/btree/5o1u.wat | 7 + benchmarks/pldi2026/btree/5o2u.wat | 7 + benchmarks/pldi2026/btree/5o3u.wat | 7 + benchmarks/pldi2026/btree/6o1u.wat | 7 + benchmarks/pldi2026/btree/6o2u.wat | 7 + benchmarks/pldi2026/btree/6o3u.wat | 7 + benchmarks/pldi2026/btree/7o1u.wat | 7 + benchmarks/pldi2026/btree/7o2u.wat | 7 + benchmarks/pldi2026/btree/7o3u.wat | 7 + benchmarks/pldi2026/btree/8o1u.wat | 7 + benchmarks/pldi2026/btree/8o2u.wat | 7 + benchmarks/pldi2026/btree/9o1u.wat | 7 + benchmarks/pldi2026/btree/9o2u.wat | 7 + benchmarks/pldi2026/btree/BTree.wast | 4080 ++++++++++++++++++++++++++ 22 files changed, 4227 insertions(+) create mode 100644 benchmarks/pldi2026/btree/BTree.wast diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index d5172a5e5..cba100334 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index 2d0a90aec..cf478938d 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index b9d56a090..9008544be 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index 17824b8c2..db7d68a91 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 01e18274f..b039177b7 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 0a929b47f..343a81270 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index e7c20f49a..a900005fe 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 8008797dc..54e2939c1 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 44eb94481..e47035320 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 961fe3dd8..22c4b48ce 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 02a3a0e95..c569b08f3 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index 8d609fbae..a3dc653b1 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 33292ec48..4fd63a13d 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 24fe6fd10..39e34e020 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index bfa1a2b15..d3659dda8 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 1b9fee44a..6e8e65182 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 783374a18..1d0d8049c 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 9fb9a51ab..df75ebc30 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index be3cc6b68..7c5dcb276 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index 73f3820f0..c6007519e 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 3ecf8dbf2..7f699c1e3 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -1,4 +1,11 @@ (module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) (memory $0 1) diff --git a/benchmarks/pldi2026/btree/BTree.wast b/benchmarks/pldi2026/btree/BTree.wast new file mode 100644 index 000000000..04a721596 --- /dev/null +++ b/benchmarks/pldi2026/btree/BTree.wast @@ -0,0 +1,4080 @@ +(module + (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) + + (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) + + (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) + + (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (sym_int32 "a") + (sym_int32 "b") + (i32.ne) + + (;);;c + (sym_int32 "c") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne);) + + (;);;d + (sym_int32 "d") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne);) + + (;;;e + (sym_int32 "e") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne);) + + (;);; f + (sym_int32 "f") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (sym_int32 "g") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; z + (sym_int32 "z") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "g") + (i32.ne);) + + + + ;; logical order: a>b>c>d>e>f>g>z + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (;(get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s);) + + (;(get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s);) + + (;(get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s);) + + (;(get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "z") + (i32.gt_s);) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (sym_int32 "h") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "z") + (i32.ne);) + + + + ;; i + (sym_int32 "i") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "z") + (i32.ne);) + + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (sym_int32 "j") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (;(get_sym_int32 "j") + (get_sym_int32 "g") + (i32.ne););) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (;(get_sym_int32 "c") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "d") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "e") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "z") + (call $btreeInsert) + (local.set 0);) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (;(local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "z") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (;);; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + (;);; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + ;; e + (;(local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + (;);; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; z + (local.get 0) + (get_sym_int32 "z") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "z") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + +) +(invoke "main") From c82a8e3e6ee907d03a3979e6c5c95feb4ec919ee Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:21:19 -0400 Subject: [PATCH 058/105] replace call to i32.symbolic with external call --- benchmarks/pldi2026/btree/2o2u.wat | 8 ++++---- benchmarks/pldi2026/btree/2o3u.wat | 10 +++++----- benchmarks/pldi2026/btree/3o1u.wat | 8 ++++---- benchmarks/pldi2026/btree/3o2u.wat | 10 +++++----- benchmarks/pldi2026/btree/3o3u.wat | 12 ++++++------ benchmarks/pldi2026/btree/4o1u.wat | 10 +++++----- benchmarks/pldi2026/btree/4o2u.wat | 12 ++++++------ benchmarks/pldi2026/btree/4o3u.wat | 14 +++++++------- benchmarks/pldi2026/btree/5o1u.wat | 12 ++++++------ benchmarks/pldi2026/btree/5o2u.wat | 14 +++++++------- benchmarks/pldi2026/btree/5o3u.wat | 16 ++++++++-------- benchmarks/pldi2026/btree/6o1u.wat | 14 +++++++------- benchmarks/pldi2026/btree/6o2u.wat | 16 ++++++++-------- benchmarks/pldi2026/btree/6o3u.wat | 18 +++++++++--------- benchmarks/pldi2026/btree/7o1u.wat | 16 ++++++++-------- benchmarks/pldi2026/btree/7o2u.wat | 18 +++++++++--------- benchmarks/pldi2026/btree/7o3u.wat | 20 ++++++++++---------- benchmarks/pldi2026/btree/8o1u.wat | 18 +++++++++--------- benchmarks/pldi2026/btree/9o1u.wat | 20 ++++++++++---------- benchmarks/pldi2026/btree/9o2u.wat | 22 +++++++++++----------- 20 files changed, 144 insertions(+), 144 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index cba100334..62315a440 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3555,9 +3555,9 @@ ;; 2 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b @@ -3571,7 +3571,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3581,7 +3581,7 @@ ;; i (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index cf478938d..fe9a9c904 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3555,9 +3555,9 @@ ;; 2 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b @@ -3571,7 +3571,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (sym_int32 "a") (i32.ne) @@ -3581,7 +3581,7 @@ ;; i (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3596,7 +3596,7 @@ ;; j (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index 9008544be..ebf7c3049 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3555,14 +3555,14 @@ ;; 3 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3588,7 +3588,7 @@ ;; 1 symbolic variable w/o order ;; h (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index db7d68a91..16fb2ade6 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3555,14 +3555,14 @@ ;; 3 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3588,7 +3588,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3602,7 +3602,7 @@ ;; i (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index b039177b7..1598c2bee 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3555,14 +3555,14 @@ ;; 3 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3588,7 +3588,7 @@ ;; 3 symbolic variables w/o order ;; h (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3602,7 +3602,7 @@ ;; i (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3621,7 +3621,7 @@ ;; j (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 343a81270..b1eb3c93d 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3555,14 +3555,14 @@ ;; 4 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3609,7 +3609,7 @@ ;; 1 symbolic variables w/o order ;; h (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index a900005fe..51cc1247e 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3555,14 +3555,14 @@ ;; 4 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3609,7 +3609,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3627,7 +3627,7 @@ ;; i (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 54e2939c1..4078da382 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3555,14 +3555,14 @@ ;; 4 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3609,7 +3609,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3627,7 +3627,7 @@ ;; i (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3650,7 +3650,7 @@ ;; j (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index e47035320..4f017f4ca 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3637,7 +3637,7 @@ ;; 1 symbolic variable w/o order ;; h (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 22c4b48ce..f7089ed7d 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3637,7 +3637,7 @@ ;; 2 symbolic variable w/o order ;; h (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3659,7 +3659,7 @@ ;; i (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index c569b08f3..b100e5718 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3637,7 +3637,7 @@ ;; 3 symbolic variable w/o order ;; h (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3659,7 +3659,7 @@ ;; i (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3685,7 +3685,7 @@ ;; j (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index a3dc653b1..bec696f54 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3555,14 +3555,14 @@ ;; 6 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3671,7 +3671,7 @@ ;; 1 symbolic variables w/o order ;; h (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 4fd63a13d..f1bb7de7e 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3555,14 +3555,14 @@ ;; 6 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3671,7 +3671,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3697,7 +3697,7 @@ ;; i (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 39e34e020..89c8c8f79 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3555,14 +3555,14 @@ ;; 6 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3671,7 +3671,7 @@ ;; 3 symbolic variables w/o order ;; h (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3697,7 +3697,7 @@ ;; i (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3727,7 +3727,7 @@ ;; i (i32.const 1040) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index d3659dda8..8167b2d5e 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3706,7 +3706,7 @@ ;; 1 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 6e8e65182..7223a70f3 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3706,7 +3706,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3737,7 +3737,7 @@ ;; i (i32.const 1040) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 1d0d8049c..0b3bf50a9 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3706,7 +3706,7 @@ ;; 3 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3737,7 +3737,7 @@ ;; i (i32.const 1040) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3771,7 +3771,7 @@ ;; i (i32.const 1042) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index df75ebc30..f53b1c337 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3652,7 +3652,7 @@ ;; x (i32.const 1044) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3748,7 +3748,7 @@ ;; 1 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index c6007519e..f26a939da 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -3555,14 +3555,14 @@ ;; 5 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3652,7 +3652,7 @@ ;; x (i32.const 1044) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3682,7 +3682,7 @@ ;; y (i32.const 1046) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3795,7 +3795,7 @@ ;; 1 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 7f699c1e3..6beffc85c 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -3555,14 +3555,14 @@ ;; 9 symbolic variables w/ order ;; a and b (i32.const 1024) - (i32.symbolic) + (call $i32.symbolic) (i32.const 1026) - (i32.symbolic) + (call $i32.symbolic) (i32.ne) ;;c (i32.const 1028) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3572,7 +3572,7 @@ ;;d (i32.const 1030) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3586,7 +3586,7 @@ ;;e (i32.const 1032) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3604,7 +3604,7 @@ ;; f (i32.const 1034) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3626,7 +3626,7 @@ ;; g (i32.const 1036) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3652,7 +3652,7 @@ ;; x (i32.const 1044) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3682,7 +3682,7 @@ ;; y (i32.const 1046) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3795,7 +3795,7 @@ ;; 2 symbolic variables w/o order ;; h (i32.const 1038) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) @@ -3833,7 +3833,7 @@ ;; i (i32.const 1040) - (i32.symbolic) + (call $i32.symbolic) (get_sym_int32 "a") (i32.ne) From 3e6964ec20473acb4b6fb722ec41b89c4a18fd33 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:44:44 -0400 Subject: [PATCH 059/105] a normalize script --- benchmarks/pldi2026/btree/normalize.py | 31 ++++++++++++++++++++++++++ 1 file changed, 31 insertions(+) create mode 100644 benchmarks/pldi2026/btree/normalize.py diff --git a/benchmarks/pldi2026/btree/normalize.py b/benchmarks/pldi2026/btree/normalize.py new file mode 100644 index 000000000..ab02461df --- /dev/null +++ b/benchmarks/pldi2026/btree/normalize.py @@ -0,0 +1,31 @@ +from pathlib import Path +import re + +pat = re.compile( + r'\(data\b\s+\$\S+\s+\(i32\.const\s+([0-9]+)\)\s*"((?:[^"\\]|\\.)*)"\)' +) + +def get_mapping(f: Path) -> list[tuple[int, str]]: + for line in f.read_text().splitlines(): + for m in pat.finditer(line): + base_str = m.group(1) + mapping_str = m.group(2) + keys = mapping_str.split("\\00") + assert(keys[-1] == "") + keys = keys[:-1] + return [(int(base_str) + i * 2, k) for i, k in enumerate(keys)] + + +def main(): + for file in Path(__file__).parent.glob("*.wat"): + mapping = get_mapping(file) + print(f"Mapping for {file.name}: {mapping}") + for addr, key in mapping: + # replace (get_sym_int32 "{key}") to (i32.const {addr})\n\t(call $i32.symbolic) in the file + file_contents = file.read_text() + file_contents = file_contents.replace(f'(get_sym_int32 "{key}")', f'(i32.const {addr})\n\t\t(call $i32.symbolic)') + file.write_text(file_contents) + + +if __name__ == "__main__": + main() From 46df39c4130e9ac8e8c9b7baac50470fb5f8b1d1 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:46:35 -0400 Subject: [PATCH 060/105] replace sym_assume with (call $i32.sym_assume) --- benchmarks/pldi2026/btree/2o2u.wat | 2 +- benchmarks/pldi2026/btree/2o3u.wat | 2 +- benchmarks/pldi2026/btree/3o1u.wat | 2 +- benchmarks/pldi2026/btree/3o2u.wat | 2 +- benchmarks/pldi2026/btree/3o3u.wat | 2 +- benchmarks/pldi2026/btree/4o1u.wat | 2 +- benchmarks/pldi2026/btree/4o2u.wat | 2 +- benchmarks/pldi2026/btree/4o3u.wat | 2 +- benchmarks/pldi2026/btree/5o1u.wat | 2 +- benchmarks/pldi2026/btree/5o2u.wat | 2 +- benchmarks/pldi2026/btree/5o3u.wat | 2 +- benchmarks/pldi2026/btree/6o1u.wat | 2 +- benchmarks/pldi2026/btree/6o2u.wat | 2 +- benchmarks/pldi2026/btree/6o3u.wat | 2 +- benchmarks/pldi2026/btree/7o1u.wat | 2 +- benchmarks/pldi2026/btree/7o2u.wat | 2 +- benchmarks/pldi2026/btree/7o3u.wat | 2 +- benchmarks/pldi2026/btree/8o1u.wat | 2 +- benchmarks/pldi2026/btree/8o2u.wat | 2 +- benchmarks/pldi2026/btree/9o1u.wat | 2 +- benchmarks/pldi2026/btree/9o2u.wat | 2 +- benchmarks/pldi2026/btree/BTree.wast | 2 +- 22 files changed, 22 insertions(+), 22 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 62315a440..de69374d7 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3598,7 +3598,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index fe9a9c904..dba9a8334 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3622,7 +3622,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index ebf7c3049..5c4d815ea 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3604,7 +3604,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index 16fb2ade6..e70aa6d18 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3626,7 +3626,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 1598c2bee..0ebe5310d 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3654,7 +3654,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index b1eb3c93d..e04b2766c 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3630,7 +3630,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 51cc1247e..5b2b5a3c8 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3657,7 +3657,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 4078da382..d5ed711fc 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3690,7 +3690,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 4f017f4ca..b2593f87e 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3663,7 +3663,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index f7089ed7d..7759304df 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3695,7 +3695,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index b100e5718..14212a7c5 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3732,7 +3732,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index bec696f54..237bb88c2 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3701,7 +3701,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index f1bb7de7e..71f68a588 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3738,7 +3738,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 89c8c8f79..734799db3 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3780,7 +3780,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 8167b2d5e..49360beef 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3742,7 +3742,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 7223a70f3..e7a6a0953 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3785,7 +3785,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 0b3bf50a9..90e04a3c5 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -3832,7 +3832,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index f53b1c337..3c95b9599 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3789,7 +3789,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index 7c5dcb276..f8a32377d 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -3826,7 +3826,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index f26a939da..f0b751cbf 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -3842,7 +3842,7 @@ (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 6beffc85c..f417dd5ad 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -3894,7 +3894,7 @@ (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") diff --git a/benchmarks/pldi2026/btree/BTree.wast b/benchmarks/pldi2026/btree/BTree.wast index 04a721596..86ddc11b5 100644 --- a/benchmarks/pldi2026/btree/BTree.wast +++ b/benchmarks/pldi2026/btree/BTree.wast @@ -3828,7 +3828,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assume) + (call $i32.sym_assume) ;; insert variables (get_sym_int32 "a") From 6425d3808159a30a1ac98e41b6d1e337637c4297 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:47:27 -0400 Subject: [PATCH 061/105] remove print_btree, it's a dummy instruction only implemented in wasp --- benchmarks/pldi2026/btree/2o1u.wat | 4 ++-- benchmarks/pldi2026/btree/2o2u.wat | 4 ++-- benchmarks/pldi2026/btree/2o3u.wat | 4 ++-- benchmarks/pldi2026/btree/3o1u.wat | 4 ++-- benchmarks/pldi2026/btree/3o2u.wat | 4 ++-- benchmarks/pldi2026/btree/3o3u.wat | 4 ++-- benchmarks/pldi2026/btree/4o1u.wat | 4 ++-- benchmarks/pldi2026/btree/4o2u.wat | 4 ++-- benchmarks/pldi2026/btree/4o3u.wat | 4 ++-- benchmarks/pldi2026/btree/5o1u.wat | 4 ++-- benchmarks/pldi2026/btree/5o2u.wat | 4 ++-- benchmarks/pldi2026/btree/5o3u.wat | 4 ++-- benchmarks/pldi2026/btree/6o1u.wat | 4 ++-- benchmarks/pldi2026/btree/6o2u.wat | 4 ++-- benchmarks/pldi2026/btree/6o3u.wat | 4 ++-- benchmarks/pldi2026/btree/7o1u.wat | 4 ++-- benchmarks/pldi2026/btree/7o2u.wat | 4 ++-- benchmarks/pldi2026/btree/7o3u.wat | 4 ++-- benchmarks/pldi2026/btree/8o1u.wat | 4 ++-- benchmarks/pldi2026/btree/8o2u.wat | 4 ++-- benchmarks/pldi2026/btree/9o1u.wat | 4 ++-- benchmarks/pldi2026/btree/9o2u.wat | 4 ++-- benchmarks/pldi2026/btree/BTree.wast | 4 ++-- 23 files changed, 46 insertions(+), 46 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o1u.wat b/benchmarks/pldi2026/btree/2o1u.wat index d57fe9d25..40df604c1 100644 --- a/benchmarks/pldi2026/btree/2o1u.wat +++ b/benchmarks/pldi2026/btree/2o1u.wat @@ -3602,7 +3602,7 @@ (call $btreeInsert) (local.set 0) - ;; (print_btree) + ;; ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3663,7 +3663,7 @@ ;; (print_stack) - ;; (print_btree) + ;; ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index de69374d7..579fffd9e 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3614,7 +3614,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3685,7 +3685,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index dba9a8334..24540db9a 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3641,7 +3641,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3730,7 +3730,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index 5c4d815ea..20905c9a5 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3620,7 +3620,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3689,7 +3689,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index e70aa6d18..8f33dccf2 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3645,7 +3645,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3734,7 +3734,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 0ebe5310d..063982442 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3676,7 +3676,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3784,7 +3784,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index e04b2766c..040e92825 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3649,7 +3649,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3737,7 +3737,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 5b2b5a3c8..570c68cfe 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3679,7 +3679,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3787,7 +3787,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index d5ed711fc..4d32a327b 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3715,7 +3715,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3842,7 +3842,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index b2593f87e..457043e31 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3685,7 +3685,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3792,7 +3792,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 7759304df..a1e4badec 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3720,7 +3720,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3846,7 +3846,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 14212a7c5..0c4efe00f 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3760,7 +3760,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3905,7 +3905,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index 237bb88c2..c2280ddf9 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3726,7 +3726,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3852,7 +3852,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 71f68a588..77712bc13 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3766,7 +3766,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3911,7 +3911,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 734799db3..67f7abc6f 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3811,7 +3811,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3975,7 +3975,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 49360beef..65d91bfeb 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3770,7 +3770,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3916,7 +3916,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index e7a6a0953..97f96b667 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3816,7 +3816,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3981,7 +3981,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 90e04a3c5..2ed4b70c9 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -3866,7 +3866,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -4050,7 +4050,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 3c95b9599..eb24fdf7d 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3821,7 +3821,7 @@ (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -3985,7 +3985,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index f8a32377d..4e39fe76c 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -3861,7 +3861,7 @@ (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -4044,7 +4044,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index f0b751cbf..647fecc2b 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -3877,7 +3877,7 @@ (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -4060,7 +4060,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index f417dd5ad..3ae34bed9 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -3932,7 +3932,7 @@ (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -4134,7 +4134,7 @@ (i32.const -1) (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) diff --git a/benchmarks/pldi2026/btree/BTree.wast b/benchmarks/pldi2026/btree/BTree.wast index 86ddc11b5..d2de79bf1 100644 --- a/benchmarks/pldi2026/btree/BTree.wast +++ b/benchmarks/pldi2026/btree/BTree.wast @@ -3865,7 +3865,7 @@ (call $btreeInsert) (local.set 0) - (print_btree) + ;; (print_btree) ;; search for variables & check that they were inserted (local.get 0) @@ -4063,7 +4063,7 @@ (i32.eq) - (print_btree) + ;; (print_btree) (i32.and) (i32.and) From 4d8241a972fa0513bdb094c6d00770093f23810a Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:50:28 -0400 Subject: [PATCH 062/105] replace (sym_assert) with (call $i32.sym_assert) --- benchmarks/pldi2026/btree/2o2u.wat | 4 ++-- benchmarks/pldi2026/btree/2o3u.wat | 4 ++-- benchmarks/pldi2026/btree/3o1u.wat | 4 ++-- benchmarks/pldi2026/btree/3o2u.wat | 4 ++-- benchmarks/pldi2026/btree/3o3u.wat | 4 ++-- benchmarks/pldi2026/btree/4o1u.wat | 4 ++-- benchmarks/pldi2026/btree/4o2u.wat | 4 ++-- benchmarks/pldi2026/btree/4o3u.wat | 4 ++-- benchmarks/pldi2026/btree/5o1u.wat | 4 ++-- benchmarks/pldi2026/btree/5o2u.wat | 4 ++-- benchmarks/pldi2026/btree/5o3u.wat | 4 ++-- benchmarks/pldi2026/btree/6o1u.wat | 4 ++-- benchmarks/pldi2026/btree/6o2u.wat | 4 ++-- benchmarks/pldi2026/btree/6o3u.wat | 4 ++-- benchmarks/pldi2026/btree/7o1u.wat | 4 ++-- benchmarks/pldi2026/btree/7o2u.wat | 4 ++-- benchmarks/pldi2026/btree/7o3u.wat | 4 ++-- benchmarks/pldi2026/btree/8o1u.wat | 4 ++-- benchmarks/pldi2026/btree/8o2u.wat | 4 ++-- benchmarks/pldi2026/btree/9o1u.wat | 4 ++-- benchmarks/pldi2026/btree/9o2u.wat | 4 ++-- benchmarks/pldi2026/btree/BTree.wast | 4 ++-- 22 files changed, 44 insertions(+), 44 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 579fffd9e..5f11614aa 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3645,7 +3645,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3690,7 +3690,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index 24540db9a..29ac9c04e 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3678,7 +3678,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3736,7 +3736,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index 20905c9a5..f42ceec90 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3650,7 +3650,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3694,7 +3694,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index 8f33dccf2..80a840cdb 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3682,7 +3682,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3740,7 +3740,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 063982442..d015b60c1 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3720,7 +3720,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3791,7 +3791,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 040e92825..98c3177ae 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3686,7 +3686,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3743,7 +3743,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 570c68cfe..fb88315d1 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3723,7 +3723,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3794,7 +3794,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 4d32a327b..71c31067b 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3766,7 +3766,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3850,7 +3850,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 457043e31..8011c3e88 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3729,7 +3729,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3799,7 +3799,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index a1e4badec..06beabf1f 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3771,7 +3771,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3854,7 +3854,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 0c4efe00f..0e6cdae3f 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3818,7 +3818,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3914,7 +3914,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index c2280ddf9..099de2966 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3777,7 +3777,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3860,7 +3860,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 77712bc13..26958a815 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3824,7 +3824,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3920,7 +3920,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 67f7abc6f..81385b3fe 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3876,7 +3876,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3985,7 +3985,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 65d91bfeb..a353d9f43 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3828,7 +3828,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3925,7 +3925,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 97f96b667..a022707d0 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3881,7 +3881,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3991,7 +3991,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 2ed4b70c9..30789824f 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -3938,7 +3938,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -4061,7 +4061,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index eb24fdf7d..0ac6f6ff8 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3886,7 +3886,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -3995,7 +3995,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index 4e39fe76c..9d5987f86 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -3933,7 +3933,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -4055,7 +4055,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index 647fecc2b..ad182c5f4 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -3949,7 +3949,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -4071,7 +4071,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 3ae34bed9..24fb5f42e 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -4011,7 +4011,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -4146,7 +4146,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ) (export "main" (func $main)) (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") diff --git a/benchmarks/pldi2026/btree/BTree.wast b/benchmarks/pldi2026/btree/BTree.wast index d2de79bf1..2fd206034 100644 --- a/benchmarks/pldi2026/btree/BTree.wast +++ b/benchmarks/pldi2026/btree/BTree.wast @@ -3939,7 +3939,7 @@ (i32.and) (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) ;; delete & check that it was deleted ;; a @@ -4069,7 +4069,7 @@ (i32.and) (i32.and) - (sym_assert) + (call $i32.sym_assert) From 25cb4f2183964c3dcd542943270c22f4ddb22fa4 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:51:00 -0400 Subject: [PATCH 063/105] replace the usage of get_sym_int32 --- benchmarks/pldi2026/btree/2o2u.wat | 72 +++-- benchmarks/pldi2026/btree/2o3u.wat | 102 ++++--- benchmarks/pldi2026/btree/3o1u.wat | 78 +++-- benchmarks/pldi2026/btree/3o2u.wat | 111 ++++--- benchmarks/pldi2026/btree/3o3u.wat | 150 ++++++--- benchmarks/pldi2026/btree/4o1u.wat | 117 ++++--- benchmarks/pldi2026/btree/4o2u.wat | 156 ++++++---- benchmarks/pldi2026/btree/4o3u.wat | 201 ++++++++---- benchmarks/pldi2026/btree/5o1u.wat | 162 ++++++---- benchmarks/pldi2026/btree/5o2u.wat | 207 ++++++++----- benchmarks/pldi2026/btree/5o3u.wat | 258 ++++++++++------ benchmarks/pldi2026/btree/6o1u.wat | 213 ++++++++----- benchmarks/pldi2026/btree/6o2u.wat | 264 ++++++++++------ benchmarks/pldi2026/btree/6o3u.wat | 321 +++++++++++++------- benchmarks/pldi2026/btree/7o1u.wat | 270 +++++++++++------ benchmarks/pldi2026/btree/7o2u.wat | 327 +++++++++++++------- benchmarks/pldi2026/btree/7o3u.wat | 390 ++++++++++++++++-------- benchmarks/pldi2026/btree/8o1u.wat | 333 +++++++++++++------- benchmarks/pldi2026/btree/8o2u.wat | 390 ++++++++++++++++-------- benchmarks/pldi2026/btree/9o1u.wat | 402 ++++++++++++++++-------- benchmarks/pldi2026/btree/9o2u.wat | 471 +++++++++++++++++++---------- 21 files changed, 3330 insertions(+), 1665 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 5f11614aa..77c0e6a12 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -3561,8 +3561,10 @@ (i32.ne) ;; logical order: a>b - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) @@ -3572,25 +3574,33 @@ ;; h (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) (i32.and) @@ -3601,16 +3611,20 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3618,25 +3632,29 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3650,36 +3668,42 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat index 29ac9c04e..f3d73e19c 100644 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ b/benchmarks/pldi2026/btree/2o3u.wat @@ -3561,8 +3561,10 @@ (i32.ne) ;; logical order: a>b - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) @@ -3575,41 +3577,55 @@ (sym_int32 "a") (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; j (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) @@ -3625,19 +3641,24 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3645,31 +3666,36 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3683,48 +3709,56 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index f42ceec90..f4677125c 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -3563,20 +3563,27 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) @@ -3589,15 +3596,20 @@ ;; h (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) @@ -3607,16 +3619,20 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3624,25 +3640,29 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3655,36 +3675,42 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index 80a840cdb..c83ef8cf8 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -3563,20 +3563,27 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) @@ -3589,33 +3596,45 @@ ;; h (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) @@ -3629,19 +3648,24 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3649,31 +3673,36 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3687,48 +3716,56 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index d015b60c1..95267b18c 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -3563,21 +3563,28 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) (i32.and) @@ -3589,56 +3596,77 @@ ;; h (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; j (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) @@ -3657,22 +3685,28 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3680,37 +3714,43 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3725,60 +3765,70 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 98c3177ae..1b1043a96 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -3563,38 +3563,52 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) (i32.and) @@ -3610,19 +3624,26 @@ ;; h (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) @@ -3633,19 +3654,24 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3653,31 +3679,36 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3691,48 +3722,56 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index fb88315d1..44c5f554b 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -3563,38 +3563,52 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) (i32.and) @@ -3610,41 +3624,57 @@ ;; h (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) @@ -3660,22 +3690,28 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3683,37 +3719,43 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3728,60 +3770,70 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 71c31067b..2f88a00bc 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -3563,38 +3563,52 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) (i32.and) @@ -3610,68 +3624,95 @@ ;; h (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; j (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) @@ -3693,25 +3734,32 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3719,43 +3767,50 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3771,72 +3826,84 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 8011c3e88..7cc60d180 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -3563,60 +3563,83 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) @@ -3638,23 +3661,32 @@ ;; h (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) @@ -3666,22 +3698,28 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3689,37 +3727,43 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3734,60 +3778,70 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 06beabf1f..bc619abd5 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -3563,60 +3563,83 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) @@ -3638,49 +3661,69 @@ ;; h (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) @@ -3698,25 +3741,32 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3724,43 +3774,50 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3776,72 +3833,84 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 0e6cdae3f..638f7311f 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -3563,60 +3563,83 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) @@ -3638,79 +3661,112 @@ ;; h (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; j (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) @@ -3735,28 +3791,36 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3764,49 +3828,57 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3823,84 +3895,98 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index 099de2966..ba2db5371 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -3563,87 +3563,121 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) @@ -3672,27 +3706,38 @@ ;; h (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) (i32.and) @@ -3704,25 +3749,32 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3730,43 +3782,50 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3782,72 +3841,84 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 26958a815..e8e185599 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -3563,87 +3563,121 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) @@ -3672,57 +3706,81 @@ ;; h (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) (i32.and) @@ -3741,28 +3799,36 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3770,49 +3836,57 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3829,84 +3903,98 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 81385b3fe..960e001d3 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -3563,87 +3563,121 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) @@ -3672,91 +3706,130 @@ ;; h (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1040) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "c") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "d") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "e") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "f") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) (i32.and) @@ -3783,31 +3856,40 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1040) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3815,55 +3897,64 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3881,96 +3972,112 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index a353d9f43..59100ae3e 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -3563,116 +3563,163 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) @@ -3707,31 +3754,44 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) @@ -3745,28 +3805,36 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3774,49 +3842,57 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3833,84 +3909,98 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index a022707d0..a81d89683 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -3563,116 +3563,163 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) @@ -3707,66 +3754,94 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1040) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "g") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) @@ -3788,31 +3863,40 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3820,55 +3904,64 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3886,96 +3979,112 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 30789824f..7a8e06f28 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -3563,116 +3563,163 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) @@ -3707,104 +3754,149 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1040) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "g") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1042) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "b") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "c") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "d") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "e") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "f") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "g") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "h") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "j") - (get_sym_int32 "i") + (i32.const 1042) + (call $i32.symbolic) + (i32.const 1040) + (call $i32.symbolic) (i32.ne) @@ -3835,34 +3927,44 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "j") + (i32.const 1042) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3870,61 +3972,71 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "j") + (i32.const 1042) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3943,108 +4055,126 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; i (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 0ac6f6ff8..266329c29 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -3563,150 +3563,212 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; x (i32.const 1044) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "b") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "c") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "d") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "e") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "f") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "g") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g>x - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "g") - (get_sym_int32 "x") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.gt_s) @@ -3749,35 +3811,50 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "x") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) @@ -3792,31 +3869,40 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3825,55 +3911,64 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3891,96 +3986,112 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; x (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat index 9d5987f86..87bd74d3c 100644 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ b/benchmarks/pldi2026/btree/8o2u.wat @@ -3560,145 +3560,207 @@ ;;c (sym_int32 "c") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (sym_int32 "d") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (sym_int32 "e") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (sym_int32 "f") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (sym_int32 "g") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; x (sym_int32 "x") - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "b") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "c") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "d") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "e") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "f") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "g") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g>x - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "g") - (get_sym_int32 "x") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.gt_s) @@ -3743,32 +3805,46 @@ (sym_int32 "a") (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "x") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) ;; i @@ -3776,36 +3852,52 @@ (sym_int32 "a") (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "g") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "x") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) @@ -3829,34 +3921,44 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3865,61 +3967,71 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3938,108 +4050,126 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; x (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index ad182c5f4..0202feebe 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -3563,188 +3563,267 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; x (i32.const 1044) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "b") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "c") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "d") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "e") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "f") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "g") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; y (i32.const 1046) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "b") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "c") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "d") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "e") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "f") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "g") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "x") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g>x>y - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "g") - (get_sym_int32 "x") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "x") - (get_sym_int32 "y") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1046) + (call $i32.symbolic) (i32.gt_s) @@ -3796,39 +3875,56 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "x") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "y") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1046) + (call $i32.symbolic) (i32.ne) @@ -3845,34 +3941,44 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3881,61 +3987,71 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -3954,108 +4070,126 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; x (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; y (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index 24fb5f42e..c33af0952 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -3563,188 +3563,267 @@ ;;c (i32.const 1028) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "c") - (get_sym_int32 "b") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) ;;d (i32.const 1030) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "b") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "d") - (get_sym_int32 "c") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) ;;e (i32.const 1032) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "b") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "c") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "e") - (get_sym_int32 "d") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) ;; f (i32.const 1034) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "b") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "c") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "d") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "f") - (get_sym_int32 "e") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) ;; g (i32.const 1036) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "b") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "c") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "d") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "e") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "g") - (get_sym_int32 "f") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) ;; x (i32.const 1044) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "b") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "c") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "d") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "e") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "f") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "x") - (get_sym_int32 "g") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) ;; y (i32.const 1046) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "b") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "c") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "d") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "e") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "f") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "g") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "y") - (get_sym_int32 "x") + (i32.const 1046) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) ;; logical order: a>b>c>d>e>f>g>x>y - (get_sym_int32 "a") - (get_sym_int32 "b") + (i32.const 1024) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "b") - (get_sym_int32 "c") + (i32.const 1026) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "c") - (get_sym_int32 "d") + (i32.const 1028) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "d") - (get_sym_int32 "e") + (i32.const 1030) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "e") - (get_sym_int32 "f") + (i32.const 1032) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "f") - (get_sym_int32 "g") + (i32.const 1034) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "g") - (get_sym_int32 "x") + (i32.const 1036) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.gt_s) - (get_sym_int32 "x") - (get_sym_int32 "y") + (i32.const 1044) + (call $i32.symbolic) + (i32.const 1046) + (call $i32.symbolic) (i32.gt_s) @@ -3796,81 +3875,117 @@ ;; h (i32.const 1038) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "b") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "c") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "d") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "e") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "f") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "g") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "x") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "h") - (get_sym_int32 "y") + (i32.const 1038) + (call $i32.symbolic) + (i32.const 1046) + (call $i32.symbolic) (i32.ne) ;; i (i32.const 1040) (call $i32.symbolic) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "b") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1026) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "c") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1028) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "d") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1030) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "e") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1032) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "f") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1034) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "g") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1036) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "x") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1044) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "y") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1046) + (call $i32.symbolic) (i32.ne) - (get_sym_int32 "i") - (get_sym_int32 "h") + (i32.const 1040) + (call $i32.symbolic) + (i32.const 1038) + (call $i32.symbolic) (i32.ne) @@ -3897,37 +4012,48 @@ (call $i32.sym_assume) ;; insert variables - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeInsert) (local.set 0) @@ -3936,67 +4062,78 @@ ;; search for variables & check that they were inserted (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) (local.get 0) - (get_sym_int32 "i") + (i32.const 1040) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.ne) @@ -4016,120 +4153,140 @@ ;; delete & check that it was deleted ;; a (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "a") + (i32.const 1024) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; b (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "b") + (i32.const 1026) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; c (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "c") + (i32.const 1028) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; d (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "d") + (i32.const 1030) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; e (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "e") + (i32.const 1032) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; f (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "f") + (i32.const 1034) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; g (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "g") + (i32.const 1036) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; x (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "x") + (i32.const 1044) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; y (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "y") + (i32.const 1046) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) ;; h (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeDelete) (local.set 0) (local.get 0) - (get_sym_int32 "h") + (i32.const 1038) + (call $i32.symbolic) (call $btreeSearch) (i32.const -1) (i32.eq) From 18e0b6bff1752861e470f55e65b0059249d1b4ba Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:55:28 -0400 Subject: [PATCH 064/105] remove two files that are not runable by wasp --- benchmarks/pldi2026/btree/2o3u.wat | 3781 ------------------------- benchmarks/pldi2026/btree/8o2u.wat | 4196 ---------------------------- 2 files changed, 7977 deletions(-) delete mode 100644 benchmarks/pldi2026/btree/2o3u.wat delete mode 100644 benchmarks/pldi2026/btree/8o2u.wat diff --git a/benchmarks/pldi2026/btree/2o3u.wat b/benchmarks/pldi2026/btree/2o3u.wat deleted file mode 100644 index f3d73e19c..000000000 --- a/benchmarks/pldi2026/btree/2o3u.wat +++ /dev/null @@ -1,3781 +0,0 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 2 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1028) - (call $i32.symbolic) - (sym_int32 "a") - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - - ;; j - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00h\00i\00j\00") -) - diff --git a/benchmarks/pldi2026/btree/8o2u.wat b/benchmarks/pldi2026/btree/8o2u.wat deleted file mode 100644 index 87bd74d3c..000000000 --- a/benchmarks/pldi2026/btree/8o2u.wat +++ /dev/null @@ -1,4196 +0,0 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (sym_int32 "a") - (sym_int32 "b") - (i32.ne) - - ;;c - (sym_int32 "c") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (sym_int32 "d") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (sym_int32 "e") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (sym_int32 "f") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (sym_int32 "g") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; x - (sym_int32 "x") - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g>x - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (sym_int32 "h") - (sym_int32 "a") - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - ;; i - (sym_int32 "i") - (sym_int32 "a") - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; x - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") -) - From 7968700fa91c31dd9d20cfa4161a7435b3e698da Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 21:57:08 -0400 Subject: [PATCH 065/105] convert all wat file to a form we can parse via (wasm2wat . wat2wasm) --- benchmarks/pldi2026/btree/2o1u.wat | 6332 ++++++++++------------- benchmarks/pldi2026/btree/2o2u.wat | 6421 ++++++++++-------------- benchmarks/pldi2026/btree/3o1u.wat | 6433 ++++++++++-------------- benchmarks/pldi2026/btree/3o2u.wat | 6537 ++++++++++-------------- benchmarks/pldi2026/btree/3o3u.wat | 6654 +++++++++++------------- benchmarks/pldi2026/btree/4o1u.wat | 6548 ++++++++++-------------- benchmarks/pldi2026/btree/4o2u.wat | 6665 +++++++++++------------- benchmarks/pldi2026/btree/4o3u.wat | 6795 +++++++++++-------------- benchmarks/pldi2026/btree/5o1u.wat | 6676 +++++++++++-------------- benchmarks/pldi2026/btree/5o2u.wat | 6807 +++++++++++-------------- benchmarks/pldi2026/btree/5o3u.wat | 6946 +++++++++++-------------- benchmarks/pldi2026/btree/6o1u.wat | 6818 +++++++++++-------------- benchmarks/pldi2026/btree/6o2u.wat | 6961 +++++++++++--------------- benchmarks/pldi2026/btree/6o3u.wat | 7116 +++++++++++--------------- benchmarks/pldi2026/btree/7o1u.wat | 6973 +++++++++++--------------- benchmarks/pldi2026/btree/7o2u.wat | 7129 +++++++++++--------------- benchmarks/pldi2026/btree/7o3u.wat | 7300 ++++++++++++--------------- benchmarks/pldi2026/btree/8o1u.wat | 7141 +++++++++++--------------- benchmarks/pldi2026/btree/9o1u.wat | 7323 ++++++++++++--------------- benchmarks/pldi2026/btree/9o2u.wat | 7504 ++++++++++++---------------- 20 files changed, 57896 insertions(+), 79183 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o1u.wat b/benchmarks/pldi2026/btree/2o1u.wat index 40df604c1..99f628164 100644 --- a/benchmarks/pldi2026/btree/2o1u.wat +++ b/benchmarks/pldi2026/btree/2o1u.wat @@ -1,3677 +1,2655 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 2 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.and) - - ;; 1 symbolic variable w/o order - ;; h - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - ;; (print_stack) - (i32.const -1) - (i32.eq) - ;; (print_stack) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - ;; (print_stack) - (i32.const -1) - (i32.eq) - ;; (print_stack) - - - ;; ;; (print_btree) - - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00h\00")) +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.and + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00h\00")) diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 77c0e6a12..9922fcc42 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -1,3725 +1,2696 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 2 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00h\00i\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.and + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00h\00i\00")) diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index f4677125c..5f8232df6 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -1,3731 +1,2702 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 3 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variable w/o order - ;; h - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index c83ef8cf8..ec97e5903 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -1,3788 +1,2749 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 3 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 95267b18c..60d0483be 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -1,3852 +1,2802 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 3 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - - ;; logical order: a>b>c - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 3 symbolic variables w/o order - ;; h - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - - ;; j - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 1b1043a96..6dfc71a31 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -1,3793 +1,2755 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 4 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variables w/o order - ;; h - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 44c5f554b..4beac7a48 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -1,3857 +1,2808 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 4 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 2f88a00bc..1fac09846 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -1,3928 +1,2867 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 4 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - ;; j - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 7cc60d180..1ef41296a 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -1,3862 +1,2814 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variable w/o order - ;; h - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index bc619abd5..432244e36 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -1,3934 +1,2873 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variable w/o order - ;; h - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 638f7311f..058891947 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -1,4008 +1,2938 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 3 symbolic variable w/o order - ;; h - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; j - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index ba2db5371..7302e3507 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -1,3939 +1,2879 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 6 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - ;; logical order: a>b>c>d>e>f - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - - ;; 1 symbolic variables w/o order - ;; h - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index e8e185599..8c22aa9c1 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -1,4017 +1,2944 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 6 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - ;; logical order: a>b>c>d>e>f - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index 960e001d3..ee7d08bb5 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -1,4101 +1,3015 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 6 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - - ;; logical order: a>b>c>d>e>f - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - - ;; 3 symbolic variables w/o order - ;; h - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1038 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + i32.const 1040 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1040 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1038 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 59100ae3e..576560feb 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -1,4023 +1,2950 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index a81d89683..d8c85450a 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -1,4108 +1,3021 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - - ;; i - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1038 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + i32.const 1040 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1040 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1038 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 7a8e06f28..0f7fd87aa 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -1,4202 +1,3098 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 3 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - - ;; i - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1042) - (call $i32.symbolic) - (i32.const 1040) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1042) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1042) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; i - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - - - - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1038 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1038 + call 0 + i32.ne + i32.const 1042 + call 0 + i32.const 1040 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + i32.const 1040 + call 0 + call 8 + local.set 0 + i32.const 1042 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1040 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1042 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1038 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1040 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1040 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00")) diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 266329c29..9f76c0a17 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -1,4114 +1,3027 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; x - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g>x - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; x - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.const 1036 + call 0 + i32.const 1044 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1044 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1044 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00")) diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index 0202feebe..8686ccde9 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -1,4213 +1,3110 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 5 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; x - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - ;; y - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g>x>y - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1046) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 1 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1046) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; x - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; y - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.const 1036 + call 0 + i32.const 1044 + call 0 + i32.gt_s + i32.const 1044 + call 0 + i32.const 1046 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1046 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1044 + call 0 + call 8 + local.set 0 + i32.const 1046 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1046 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1044 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1046 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1046 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00")) diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index c33af0952..fff6815d5 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -1,4311 +1,3193 @@ -(module - (import "i32" "symbolic" (func $i32.symbolic (param i32) (result i32))) - - (import "i32" "sym_assume" (func $i32.sym_assume (param i32))) - - (import "i32" "sym_assert" (func $i32.sym_assert (param i32))) - - (import "sym" "get_sym_int32" (func $get_sym_int32 (param i32) (result i32))) - (memory $0 1) - - - (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree - (i32.const 0) - (local.get 0) - (i32.store) ;; store t at address 0 - - (i32.const 0) - (i32.const 1) - (i32.store offset=4) ;; store the number of nodes in the btree = 1 - - (i32.const 0) - (i32.const 65536) - (i32.store offset=8) ;; store the root addr - - (i32.const 1) ;; Now create root - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then - (i32.const 65536) ;; 64KiB = 65536 bytes - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - - (i32.const 65536) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - ) - ) - (i32.const 65536) ;; returns the address of the root - ) - - ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. - (func $btreeSearch (param i32) (param i32) (result i32) (local i32) - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n -1 - (i32.le_s) ;; i <= x.children-1 - (if - (then - (local.get 1) ;; k - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - (if - (then - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) ;; i - - (local.get 0) ;; x - (i32.load offset=4) ;; x.children - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.le_s) ;; i <= x.children - 1 - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.eq) - ;; k == x.keys[i] - (if (result i32) - (then - - (local.get 0) ;; save the address, which is x+8+i*4 - (i32.const 8) - (i32.add) ;; x+8 - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x+8+i*4 - - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - (else - (local.get 0) ;; x - (i32.load) ;; x is leaf? - (i32.const 1) ;; if == 1, then yes - (i32.eq) - (if (result i32) - (then - (i32.const -1) - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i - - (local.get 1) ;; k - - (call $btreeSearch) ;; btreeSearch(x.children[i], k) - - ) - ) - ) - ) - ) - - ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x - (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if ;; if we can grow memory - (then ;; get the number of nodes in the tree - (i32.const 0) - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address is 64KiB*(number of nodes+1) - (local.set 2) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - - (i32.load offset=8) ;; load the addr of the child in index i : y - - - (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child - (i32.const 1) - (i32.eq) ;; is y leaf? - (if - (then ;; yes - (local.get 2) ;; addr of new node z - (i32.const 1) - (i32.store) ;; store 1(TRUE) regarding if node is leaf - ) - (else ;; no - (local.get 2) ;; addr of new node z - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - ) - ) - - (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - - (i32.store offset=4) ;; store number of children = (t/2)-1 - - (i32.const 0) ;; now to store the keys - (local.set 3) ;; counter = 0 - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.const 1) - (i32.sub) ;; (t/2)-1 - (i32.eq) ;; counter == (t/2)-1 - (if - (then - - (br $loop_break) - ) - (else - - (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] - - (i32.const 4) - (local.get 3) ;; counter - - (i32.mul) ;; counter * 4 - - (i32.add) ;; addr + counter * 4 -> where the key is goint to be located - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.add) ;; counter + (t/2) - - (i32.mul) ;; counter + (t/2) *4 - - (i32.add) ;; y + counter + (t/2) *4 - (i32.load offset=8) ;; y.keys[counter + (t/2)] - - (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] - - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - - ) - ) - ) - ) - - (i32.const 0) - (local.set 3) ;; set counter back to 0 - - (i32.const 0) ;; check if x.children[i] is leaf - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + i*4 - (i32.load offset=8) ;; load the address of the child in index i = y - (i32.load) ;; get first i32 in child --> isLeaf - (i32.const 1) - (i32.ne) ;; is leaf? - - (if - (then ;; not leaf so we have to update the children - (block $loop_break - (loop $loop - - (local.get 3) ;; counter - - (i32.const 0) - (i32.load) ;; t - - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.eq) ;; counter == (t/2) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; now get z.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; counter*4 - - (i32.add) ;; (t-1)*4 + counter*4 - - (local.get 2) ;; z - (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) ;; get x.children[i].children[counter+(t/2)] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.add) ;; counter + t/2 - (i32.const 4) - (i32.mul) ;; counter+t/2 * 4 - - (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 - - (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 - (i32.load offset=8) ;; load the address of the child in index counter + t/2 - - (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] - - (local.get 3) ;; increment counter - (i32.const 1) - (i32.add) - (local.set 3) - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 - - (local.get 0) ;; x - - (i32.load offset=4) ;; get x.n - (local.set 3) ;; counter = x.n - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (local.get 3) ;; counter - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; get x.children[counter + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (i32.add) ;; (t-1)*4 + (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored - - (i32.const 0) ;; get x.children[counter] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (i32.add) ;; (t-1)*4 + (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (counter)*4 - (i32.load offset=8) ;; load the addr of the child in index (counter) - - (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (i32.const 0) ;; get x.children[i + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 1) - (i32.add) ;; i + 1 - (i32.const 4) - (i32.mul) ;; (i + 1)*4 - - (i32.add) ;; (t-1)*4 + (i + 1)*4 - - (local.get 0) ;; x - - (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child - - (local.get 2) ;; addr of z - (i32.store offset=8) ;; x.children[i+1] = z - - (local.get 0) ;; x - (i32.load offset=4) ;; get x.n - (i32.const 1) - (i32.sub) - (local.set 3) ;; counter = x.n -1 - - (block $loop_break - (loop $loop - (local.get 1) ;; i - (i32.const 1) - (i32.sub) ;; i-1 - (local.get 3) ;; counter - (i32.eq) ;; counter == i-1 - - (if - (then - (br $loop_break) - ) - (else - - (local.get 3) ;; get x.keys[counter + 1] ;; counter - (i32.const 1) - (i32.add) ;; counter + 1 - (i32.const 4) - (i32.mul) ;; (counter + 1)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key - - (local.get 3) ;; counter - (i32.const 4) - (i32.mul) ;; (counter)*4 - - (local.get 0) ;; x - (i32.add) ;; x +(counter)*4 - (i32.load offset=8) ;; load the key in index (counter) - - (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] - - (local.get 3) ;; decrement counter - (i32.const 1) - (i32.sub) - (local.set 3) - (br $loop) - ) - ) - - ) - ) - - (local.get 1) ;; get x.keys[i] - (i32.const 4) - (i32.mul) ;; i*4 - - (local.get 0) ;; x - (i32.add) ;; x +i*4 --> addr of the key - - (i32.const 0) ;; get x.children[i].keys[t/2] - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; t/2 -1 - - (i32.const 4) - (i32.mul) ;; (t/2)-1 *4 - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 1) ;; i - (i32.const 4) - (i32.mul) ;; (i)*4 - - (i32.add) ;; (t-1)*4 + (i)*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 + (i)*4 - (i32.load offset=8) ;; load the address of the child in index (i) - - (i32.add) ;; y + (t/2)-1 *4 - (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] - - (i32.store offset=8) ;; store the new key in the addr - - (local.get 0) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) ;; x.n + 1 - (i32.store offset=4) ;; x.n = x.n + 1 - ) - ) - ) - - ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert - (func $btreeInsertNonFull (param i32) (param i32) (local i32) - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.const 1) - (i32.sub) ;; x.n -1 - (local.set 2) ;; i = x.n -1 - - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (block $loop_break - (loop $loop - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - - (if (result i32) - (then - (local.get 1) ;; k - (local.get 0) ;; x - ;; x+4*i - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - (i32.lt_s) ;; k < x.keys[i] - ) - (else - (i32.const 0) - ) - ) - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i <= 0? - (i32.and) - - (if - (then - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i *4 - - (i32.add) ;; x + i *4 --> addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 2) ;; i = i-1 - (br $loop) - - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.mul) ;; i+1 *4 - - (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.keys[i+1] = k - - (local.get 0) - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;; x.n = x.n +1 - - ) - (else ;; x is not leaf - (block $loop_break - (loop $loop - - (local.get 2) ;; i - (i32.const 0) - (i32.ge_s) ;; i >= 0 - - (if - (then - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.lt_s) ;; k < x.keys[i] - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i -1 - (local.set 2) ;; i = i-1 - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - - (i32.const 1) - (i32.add) - - (local.set 2) ;;i = i+1 - - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y - (i32.load offset=8) ;; load the address of the child in index i = y - - (i32.load offset=4) ;; get y.n - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; y.n == t-1 --> node is full - (if - (then - (local.get 0) ;; x - - (local.get 2) ;; i - (call $btreeSplitChild) - - (local.get 1) ;; k - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k>x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i+1 - ) - ) - ) - ) - - (i32.const 0) ;; get x.children[i] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; load the address of the child in index i = y - - (local.get 1) ;; k - - (call $btreeInsertNonFull) - - ) - ) - ) - - (func $btreeInsert (param i32) (result i32) (local i32) (local i32) - (i32.const 0) - (i32.load offset=8) ;; root addr - (local.tee 2) ;; set r - - (i32.load offset=4) ;; r.n - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.eq) ;; r.n == t-1 --> root is full - (if (result i32) - (then - - (i32.const 1) ;; create a new node - (memory.grow) ;; create new page - (i32.const -1) - (i32.ne) - (if (result i32) ;; if we can grow memory - (then - (i32.const 0) ;; get the number of nodes in the tree - (i32.load offset=4) ;; number of nodes in the tree - (i32.const 1) - (i32.add) ;; number of nodes + 1 - (i32.const 65536) - (i32.mul) ;; address of s is 64KiB*(number of nodes+1) - (local.set 1) - - (i32.const 0) ;; change number of nodes - (i32.const 0) - (i32.load offset=4) - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; set number of nodes to + 1 - - (i32.const 0) - (local.get 1) ;; s - (i32.store offset=8) ;; root addr is now s - - (local.get 1) ;; s - (i32.const 0) - (i32.store) ;; store 0(FALSE) regarding if node is leaf - - (local.get 1) ;; now store number of keys - (i32.const 0) - (i32.store offset=4) ;; store number of keys = 0 - - (i32.const 0) ;; store children addresses - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 1) ;; x - (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located - (local.get 2) - - (i32.store offset=8) ;; s.children[0] = r - - (local.get 1) ;; s - (i32.const 0) - - (call $btreeSplitChild) - - (local.get 1) ;; s - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 1) ;; return the address of the new root - ) - (else - (i32.const -1) ;; return -1 because we could not create a new node - ) - ) - ) - (else - (local.get 2) ;; r - (local.get 0) ;; k - (call $btreeInsertNonFull) - (local.get 2) ;; return the address of the root, which is the same - ) - ) - ) - - ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) - (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) - (local.get 0) ;; x - (i32.load) ;; get first i32 --> isLeaf - (i32.const 1) - (i32.eq) ;; is leaf? - (if - (then ;; x is leaf - (i32.const 0) - (local.set 2) ;; i = 0 - (block $loop_break - (loop $loop - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (local.get 2) ;; i - - (i32.eq) ;; i == x.n - (if - (then - (br $loop_break) ;; break from loop - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - - (i32.eq) ;; k == x.keys[i] - (if - (then - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $while_break - (loop $while - (local.get 3) ;; j - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n-1 - (i32.eq) ;; j == x.n-1 - (if - (then - (br $while_break) - ) - (else - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - - (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored - - (local.get 0) ;; x - - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.mul) ;; j+1 *4 - - (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $while) - ) - ) - - ) - ) - (local.get 0) ;; x - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.n = x.n -1 - (br $loop_break) - ) - - ) - ) - - ) - (i32.const 1) - (local.get 2) - (i32.add) - (local.set 2) ;; i = i+1 - (br $loop) ;; continue - ) - ) - ) - (else ;; x is not leaf - - (i32.const 0) ;;get the index of the appropriate child/key - (local.set 2) ;; i = 0 - - (block $loop_break - (loop $loop - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (if (result i32) - (then - (local.get 1) ;; k - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (i32.gt_s) ;; k > x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (local.get 2) ;; i - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.le_s) ;; i <= x.n - 1 - - (i32.and) ;; i <= x.n - 1 && k > x.keys[i] - - (if - (then - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (local.set 2) ;; i = i + 1 - - (br $loop) - ) - (else - (br $loop_break) - ) - ) - ) - ) - (local.get 2) - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.lt_s) ;; i < x.n - (if (result i32) - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[i] - - (local.get 1) ;; k - (i32.eq) ;; k == x.keys[i] - ) - (else - (i32.const 0) - ) - ) - (if - (then ;; key is present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.tee 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i].n >= t/2 - (if - (then - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.sub) ;; index = x.c[i].n - 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] - - (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] - - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i+1] - (local.tee 5) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (local.get 5) ;; x.c[i+1] - (local.get 5) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[0] - (call $btreeDelete) - (drop) - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - ) - (else - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i *4 - (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored - - (local.get 1) ;; k - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k - - (i32.const 0) ;; now merge x.c[i] with x.c[i+1] - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - (i32.add) ;; (t-1)*4 + i+1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - - (if ;; j == x.c[i+1].n - (then - (br $loop_break) - ) - (else - - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n + j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - - ) - - ) - ) - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n +1 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.add) - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - - (i32.const 0) ;; now adjust the children - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.get 3) ;; j - (i32.add) ;; index = x.c[i].n+j - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored - - (i32.const 0) ;;get x.c[i+1].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x.c[i+1] + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - (i32.const 1) - (i32.sub) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; j*4 - (i32.add) ;; x + j*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.add) - (i32.mul) ;; j+1*4 - (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - - ) - ) - - (local.get 2) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = i+1 - - (block $loop_break - (loop $loop - (local.get 0) - (i32.load offset=4) - - (local.get 3) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.add) ;; j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - (local.get 0) - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - (i32.store offset=4) ;; x.n = x.n-1 - - (local.get 5) ;; x.c[i] - (local.get 1) ;; k - - (call $btreeDelete) - (drop) - - ) - ) - - ) - ) - - ) - (else ;; key not present in node x - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 4) - (i32.mul) ;; i*4 - - (i32.add) ;; (t-1)*4 + i*4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located - (i32.load offset=8) ;; x.c[i] - - (local.set 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) - (i32.const 1) - (i32.sub) ;; t/2 - 1 - - (i32.eq) - - (if - (then - (i32.const -1) - (local.set 4) ;; changed = -1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.le_s) ;; i+1 <= x.n - - (if - (then - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i+1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i+1].n >= t/2 - - (if - (then - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.const 1) - (i32.sub) ;; index = t/2 -1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] - - (local.get 5) - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - - (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 - - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] - (i32.load offset=8) ;; x.c[i+1].keys[0] - - (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] - - (local.get 5) - (i32.load) ;; x.c[i] is leaf? - (i32.const 1) - (i32.ne) - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - - (i32.const 0) ;;get x.c[i].c[t/2] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; index = t/2 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] - - (i32.const 0) ;;get x.c[i+1].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[0] - - (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] - ) - ) - - (local.get 5) ;; x.c[i] - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - (i32.store offset=4) ;; x.c[i].n = t/2 - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j+1] - - (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if ;; if x.c[i] is not leaf, we have to adjust children - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j+1 - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j+1] - - (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j+1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located - (i32.load offset=8) - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - (i32.const 0) - (i32.ge_s) ;; i -1 >= 0 - - (i32.and) ;; changed == -1 && i -1 >= 0 - - (if - (then - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 0) - (i32.load) ;; t - (i32.const 2) - (i32.div_s) ;; t/2 - - (i32.ge_s) ;; x.c[i-1].n >= t/2 - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (local.set 3) ;; j = x.c[i].n - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] - (i32.load offset=8) ;; x.c[i].keys[j-1] - - (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - - (if - (then - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (local.set 3) ;; j = x.c[i].n + 1 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) - (i32.eq) - - (if - (then - (br $loop_break) - ) - (else - (i32.const 0) ;;get x.c[i].c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located - - (i32.const 0) ;;get x.c[i].c[j-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; j - (i32.const 1) - (i32.sub) ;; j-1 - (i32.const 4) - (i32.mul) ;; j *4 - - (i32.add) ;; (t-1)*4 + j *4 - - (local.get 5) ;; x.c[i] - (i32.add) - (i32.load offset=8) ;; x.c[i].c[j-1] - - (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] - - (local.get 3) - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = j-1 - - (br $loop) - ) - ) - ) - ) - ) - ) - - (local.get 5) - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) - (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 - - (local.get 5) ;; x.c[i] - (i32.const 4) - (i32.const 0) ;; index = 0 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i-1] - - (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) - (i32.load offset=4) ;; x.c[i-1].n - - (i32.const 1) - (i32.sub) - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; index = i-1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - (i32.load offset=8) - - (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - - (i32.const 0) ;; get x.c[i].c[0] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located - - (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (i32.const 1) - (i32.add) ;; index = x.c[i-1.n + 1] - - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] - - (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] - - ) - ) - (i32.const 0) - (local.set 4) ;; changed = 0 - ) - ) - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) - (if ;; changed == -1? - (then - - (local.get 2) ;; we have to merge x.c[i] with one sibling;; i - (i32.const 1) - (i32.add) ;; i+1 - - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - - (i32.le_s) - (if ;; i+1 <= x.n - (then - - (local.get 5) ;; merge with right sibling;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) ;; index = x.c[i].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - (local.get 5) ;; x.c[i] - (i32.const 4) - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i+1].keys[j] - - (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i+1].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 5) - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] - - (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1].c[j] - - (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (local.get 5) ;; x.c[i] - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.const 0) ;;get x.c[i+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i+1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i+1] - (i32.load offset=4) ;; x.c[i+1].n - - (i32.add) ;; x.c[i].n + x.c[i+1].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 - - (local.get 2) ;; i - (i32.const 1) - (i32.add) ;; i+1 - (local.set 3) ;; j = i+1 - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - ) - ) - (local.get 2) ;; i - (local.set 3) ;; j = i - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - - (i32.const 0) - (local.set 4) ;; changed = 0 - - ) - ) - - (local.get 4) ;; changed - (i32.const -1) - (i32.eq) ;; changed == -1 ? - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) ;; i - 1 - - (i32.const 0) - (i32.ge_s) ;; i - 1 >= 0? - - (i32.and) ;; changed == -1 && i - 1 >= 0 - (if - (then - - (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; index = x.c[i-1].n - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] - - (local.get 0) ;; x - (i32.const 4) - (local.get 2) ;; index = i - (i32.const 1) - (i32.sub) ;; index = i-1 - - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] - (i32.load offset=8) ;; x.keys[i] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] - - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;; x.c[i-1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.const 4) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] - - (local.get 5) ;; x.c[i] - (i32.const 4) - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.c[i].keys[j] - - (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - - (local.get 5) - (i32.load) - (i32.const 1) - (i32.ne) - (if - (then - (i32.const 0) - (local.set 3) ;; j = 0 - - (block $loop_break - (loop $loop - (local.get 3) ;; j - - (local.get 5) ;; x.c[i] - (i32.load offset=4) ;; x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + 1 - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) - (local.get 3) - (i32.add) - (i32.const 1) - (i32.add) ;; index = x.c[i-1].n+j+1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 5) ;; x.c[i] - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i].c[j] - - (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - (br $loop) - ) - ) - - ) - ) - ) - ) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (i32.load offset=4) ;; x.c[i-1].n - - (local.get 5) - (i32.load offset=4) ;; x.c[i].n - - (i32.add) ;; x.c[i-1].n + x.c[i].n - (i32.const 1) - (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 - - (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 - - (local.get 2) ;; i - (local.set 3) ;; j = i - - (block $loop_break ;; re-organize x - (loop $loop - - (local.get 3) - - (local.get 0) - (i32.load offset=4) ;; x.n - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (i32.const 0) ;;get x.c[j] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) ;; index = j - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - - (i32.const 0) ;;get x.c[j+1] - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.const 4) - (i32.mul) ;; i-1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] - (i32.load offset=8) ;; x.c[j+1] - - (i32.store offset=8) ;; x.c[j] = x.c[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (local.set 3) ;; j = i - 1 - (block $loop_break - (loop $loop - - (local.get 3) ;; j - - (local.get 0) - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) - - (i32.eq) - (if - (then - (br $loop_break) - ) - (else - - (local.get 0) ;; x - (i32.const 4) - - (local.get 3) ;; index = j - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 ;; addr of x.keys[j] - - (local.get 0) ;; x - (i32.const 4) - (local.get 3) - (i32.const 1) - (i32.add) ;; index = j + 1 - (i32.mul) ;; i*4 - (i32.add) ;; x + i*4 - (i32.load offset=8) ;; x.keys[j+1] - - (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] - - (local.get 3) - (i32.const 1) - (i32.add) - (local.set 3) ;; j = j + 1 - - (br $loop) - - ) - ) - - ) - ) - (local.get 0) ;; x - (local.get 0) ;; x - (i32.load offset=4) ;; x.n - (i32.const 1) - (i32.sub) ;; x.n - 1 - (i32.store offset=4) ;; x.n = x.n - 1 - ) - ) - ) - ) - ) - ) - (local.get 4) - (i32.const -1) - (i32.eq) - (if ;; changed == -1? if yes, we merged with left sibling - (then - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (local.get 2) ;; i - (i32.const 1) - (i32.sub) - (i32.const 4) - (i32.mul) ;; i+1 *4 - - (i32.add) ;; (t-1)*4 + i-1 *4 - - (local.get 0) ;; x - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; x.c[i-1] - (local.get 1) - (call $btreeDelete) - (drop) - ) - (else - (local.get 5) ;; x.c[i] - (local.get 1) - (call $btreeDelete) - (drop) - ) - ) - - ) - ) - ) ;; end of if x is not leaf - ) - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.load offset=4) - (i32.const 0) - (i32.eq) - (if ;; if root is empty - (then - (i32.const 0) - - (i32.const 0) - (i32.load) ;; t - (i32.const 1) - (i32.sub) ;; t-1 - (i32.const 4) - (i32.mul) ;; (t-1)*4 - - (i32.const 0) ;; index = 0 - (i32.const 4) - (i32.mul) ;; i *4 - - (i32.add) ;; (t-1)*4 + i *4 - - (i32.const 0) - (i32.load offset=8) ;; root addr - (i32.add) ;; x + (t-1)*4 - (i32.load offset=8) ;; root.c[0] - - (i32.store offset=8) ;; root = root.c[0] - ) - ) - - (i32.const 0) - (i32.load offset=8) ;; root addr - ) - - - (func $main - (local i32) - (i32.const 4) ;;create a tree with degree 4 - (call $createBtree) - (local.set 0) - - ;; 9 symbolic variables w/ order - ;; a and b - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;c - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - ;;d - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - ;;e - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - ;; f - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - ;; g - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - ;; x - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - ;; y - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1046) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - ;; logical order: a>b>c>d>e>f>g>x>y - (i32.const 1024) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1026) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1028) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1030) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1032) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1034) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1036) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.gt_s) - - (i32.const 1044) - (call $i32.symbolic) - (i32.const 1046) - (call $i32.symbolic) - (i32.gt_s) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - ;; 2 symbolic variables w/o order - ;; h - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1038) - (call $i32.symbolic) - (i32.const 1046) - (call $i32.symbolic) - (i32.ne) - - ;; i - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1024) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1026) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1028) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1030) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1032) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1034) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1036) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1044) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1046) - (call $i32.symbolic) - (i32.ne) - - (i32.const 1040) - (call $i32.symbolic) - (i32.const 1038) - (call $i32.symbolic) - (i32.ne) - - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assume) - - ;; insert variables - (i32.const 1024) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeInsert) - (local.set 0) - - - ;; (print_btree) - - ;; search for variables & check that they were inserted - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (local.get 0) - (i32.const 1040) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.ne) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (call $i32.sym_assert) - - ;; delete & check that it was deleted - ;; a - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1024) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; b - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1026) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; c - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1028) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; d - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1030) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; e - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1032) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; f - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1034) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; g - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1036) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; x - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1044) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; y - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1046) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; h - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeDelete) - (local.set 0) - - (local.get 0) - (i32.const 1038) - (call $i32.symbolic) - (call $btreeSearch) - (i32.const -1) - (i32.eq) - - ;; (print_btree) - - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - (i32.and) - - (call $i32.sym_assert) - ) - (export "main" (func $main)) - (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") -) - +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32 i32) (result i32))) + (type (;3;) (func (param i32 i32))) + (type (;4;) (func)) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (func (;4;) (type 0) (param i32) (result i32) + i32.const 0 + local.get 0 + i32.store + i32.const 0 + i32.const 1 + i32.store offset=4 + i32.const 0 + i32.const 65536 + i32.store offset=8 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 65536 + i32.const 1 + i32.store + i32.const 65536 + i32.const 0 + i32.store offset=4 + end + i32.const 65536) + (func (;5;) (type 2) (param i32 i32) (result i32) + (local i32) + i32.const 0 + local.set 2 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if ;; label = @3 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @4 + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 2 (;@2;) + else + br 3 (;@1;) + end + else + br 2 (;@1;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @1 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.eq + if (result i32) ;; label = @2 + local.get 0 + i32.const 8 + i32.add + i32.const 4 + local.get 2 + i32.mul + i32.add + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @3 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end + else + local.get 0 + i32.load + i32.const 1 + i32.eq + if (result i32) ;; label = @2 + i32.const -1 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 5 + end + end) + (func (;6;) (type 3) (param i32 i32) + (local i32 i32) + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if ;; label = @1 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 2 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.eq + if ;; label = @2 + local.get 2 + i32.const 1 + i32.store + else + local.get 2 + i32.const 0 + i32.store + end + local.get 2 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 2 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + local.set 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load + i32.const 1 + i32.ne + if ;; label = @2 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.eq + if ;; label = @5 + br 2 (;@3;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 2 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.add + i32.const 4 + i32.mul + i32.add + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@4;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + local.get 2 + i32.store offset=8 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + local.get 0 + i32.add + local.get 3 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@3;) + end + end + end + local.get 1 + i32.const 4 + i32.mul + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 1 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end) + (func (;7;) (type 3) (param i32 i32) + (local i32) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.set 2 + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + else + i32.const 0 + end + local.get 2 + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.add + i32.mul + i32.add + local.get 1 + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + else + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.const 0 + i32.ge_s + if ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.lt_s + if ;; label = @5 + local.get 2 + i32.const 1 + i32.sub + local.set 2 + br 2 (;@3;) + else + br 3 (;@2;) + end + else + br 2 (;@2;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if ;; label = @2 + local.get 0 + local.get 2 + call 6 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + if ;; label = @3 + local.get 2 + i32.const 1 + i32.add + local.set 2 + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 7 + end) + (func (;8;) (type 0) (param i32) (result i32) + (local i32 i32) + i32.const 0 + i32.load offset=8 + local.tee 2 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.eq + if (result i32) ;; label = @1 + i32.const 1 + memory.grow + i32.const -1 + i32.ne + if (result i32) ;; label = @2 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 65536 + i32.mul + local.set 1 + i32.const 0 + i32.const 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + i32.const 0 + local.get 1 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store + local.get 1 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 1 + i32.add + local.get 2 + i32.store offset=8 + local.get 1 + i32.const 0 + call 6 + local.get 1 + local.get 0 + call 7 + local.get 1 + else + i32.const -1 + end + else + local.get 2 + local.get 0 + call 7 + local.get 2 + end) + (func (;9;) (type 2) (param i32 i32) (result i32) + (local i32 i32 i32 i32) + local.get 0 + i32.load + i32.const 1 + i32.eq + if ;; label = @1 + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 2 + i32.eq + if ;; label = @4 + br 2 (;@2;) + else + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + if ;; label = @5 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + br 3 (;@2;) + end + end + i32.const 1 + local.get 2 + i32.add + local.set 2 + br 0 (;@3;) + end + end + else + i32.const 0 + local.set 2 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + if (result i32) ;; label = @4 + local.get 1 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.gt_s + else + i32.const 0 + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.le_s + i32.and + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.set 2 + br 1 (;@3;) + else + br 2 (;@2;) + end + end + end + local.get 2 + local.get 0 + i32.load offset=4 + i32.lt_s + if (result i32) ;; label = @2 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + local.get 1 + i32.eq + else + i32.const 0 + end + if ;; label = @2 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @3 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.tee 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + local.get 5 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + call 9 + drop + i32.store offset=8 + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 1 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.store offset=4 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @5 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + end + local.get 2 + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @5 + loop ;; label = @6 + local.get 0 + i32.load offset=4 + local.get 3 + i32.eq + if ;; label = @7 + br 2 (;@5;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@6;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 5 + local.get 1 + call 9 + drop + end + end + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.set 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.eq + if ;; label = @3 + i32.const -1 + local.set 4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.const 4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 1 + i32.sub + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + local.get 5 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.store offset=4 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 2 + i32.div_s + i32.ge_s + if ;; label = @5 + local.get 5 + i32.load offset=4 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.sub + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 5 + i32.const 4 + i32.const 0 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + local.set 4 + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @4 + local.get 2 + i32.const 1 + i32.add + local.get 0 + i32.load offset=4 + i32.le_s + if ;; label = @5 + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 5 + i32.const 4 + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 5 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + local.get 5 + local.get 5 + i32.load offset=4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.const 1 + i32.add + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + i32.const 0 + local.set 4 + end + local.get 4 + i32.const -1 + i32.eq + local.get 2 + i32.const 1 + i32.sub + i32.const 0 + i32.ge_s + i32.and + if ;; label = @5 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 2 + i32.const 1 + i32.sub + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + i32.const 0 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 5 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 4 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.mul + i32.add + local.get 5 + i32.const 4 + local.get 3 + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 5 + i32.load + i32.const 1 + i32.ne + if ;; label = @6 + i32.const 0 + local.set 3 + block ;; label = @7 + loop ;; label = @8 + local.get 3 + local.get 5 + i32.load offset=4 + i32.const 1 + i32.add + i32.eq + if ;; label = @9 + br 2 (;@7;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.add + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 5 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@8;) + end + end + end + end + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.load offset=4 + local.get 5 + i32.load offset=4 + i32.add + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 3 + i32.const 1 + i32.add + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 2 + i32.const 1 + i32.sub + local.set 3 + block ;; label = @6 + loop ;; label = @7 + local.get 3 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.eq + if ;; label = @8 + br 2 (;@6;) + else + local.get 0 + i32.const 4 + local.get 3 + i32.mul + i32.add + local.get 0 + i32.const 4 + local.get 3 + i32.const 1 + i32.add + i32.mul + i32.add + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.const 1 + i32.add + local.set 3 + br 1 (;@7;) + end + end + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=4 + end + end + end + local.get 4 + i32.const -1 + i32.eq + if ;; label = @3 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + local.get 2 + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.add + local.get 0 + i32.add + i32.load offset=8 + local.get 1 + call 9 + drop + else + local.get 5 + local.get 1 + call 9 + drop + end + end + end + i32.const 0 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + if ;; label = @1 + i32.const 0 + i32.const 0 + i32.load + i32.const 1 + i32.sub + i32.const 4 + i32.mul + i32.const 0 + i32.const 4 + i32.mul + i32.add + i32.const 0 + i32.load offset=8 + i32.add + i32.load offset=8 + i32.store offset=8 + end + i32.const 0 + i32.load offset=8) + (func (;10;) (type 4) + (local i32) + i32.const 4 + call 4 + local.set 0 + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1028 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1030 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1032 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1034 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1036 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1044 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1046 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.const 1024 + call 0 + i32.const 1026 + call 0 + i32.gt_s + i32.const 1026 + call 0 + i32.const 1028 + call 0 + i32.gt_s + i32.const 1028 + call 0 + i32.const 1030 + call 0 + i32.gt_s + i32.const 1030 + call 0 + i32.const 1032 + call 0 + i32.gt_s + i32.const 1032 + call 0 + i32.const 1034 + call 0 + i32.gt_s + i32.const 1034 + call 0 + i32.const 1036 + call 0 + i32.gt_s + i32.const 1036 + call 0 + i32.const 1044 + call 0 + i32.gt_s + i32.const 1044 + call 0 + i32.const 1046 + call 0 + i32.gt_s + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.const 1038 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.const 1038 + call 0 + i32.const 1046 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1024 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1026 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1028 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1030 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1032 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1034 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1036 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1044 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1046 + call 0 + i32.ne + i32.const 1040 + call 0 + i32.const 1038 + call 0 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 1 + i32.const 1024 + call 0 + call 8 + local.set 0 + i32.const 1026 + call 0 + call 8 + local.set 0 + i32.const 1028 + call 0 + call 8 + local.set 0 + i32.const 1030 + call 0 + call 8 + local.set 0 + i32.const 1032 + call 0 + call 8 + local.set 0 + i32.const 1034 + call 0 + call 8 + local.set 0 + i32.const 1036 + call 0 + call 8 + local.set 0 + i32.const 1044 + call 0 + call 8 + local.set 0 + i32.const 1046 + call 0 + call 8 + local.set 0 + i32.const 1038 + call 0 + call 8 + local.set 0 + i32.const 1040 + call 0 + call 8 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1046 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.ne + local.get 0 + i32.const 1040 + call 0 + call 5 + i32.const -1 + i32.ne + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2 + local.get 0 + i32.const 1024 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1024 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1026 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1026 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1028 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1028 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1030 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1030 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1032 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1032 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1034 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1034 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1036 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1036 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1044 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1044 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1046 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1046 + call 0 + call 5 + i32.const -1 + i32.eq + local.get 0 + i32.const 1038 + call 0 + call 9 + local.set 0 + local.get 0 + i32.const 1038 + call 0 + call 5 + i32.const -1 + i32.eq + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + i32.and + call 2) + (memory (;0;) 1) + (export "main" (func 10)) + (data (;0;) (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00")) From f88be3b4c5a370d0100269b90ef01f0fbed74524 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 22:04:13 -0400 Subject: [PATCH 066/105] get_sym_int32 is not useful anymore --- benchmarks/pldi2026/btree/2o1u.wat | 2 +- benchmarks/pldi2026/btree/2o2u.wat | 2 +- benchmarks/pldi2026/btree/3o1u.wat | 2 +- benchmarks/pldi2026/btree/3o2u.wat | 2 +- benchmarks/pldi2026/btree/3o3u.wat | 2 +- benchmarks/pldi2026/btree/4o1u.wat | 2 +- benchmarks/pldi2026/btree/4o2u.wat | 2 +- benchmarks/pldi2026/btree/4o3u.wat | 2 +- benchmarks/pldi2026/btree/5o1u.wat | 2 +- benchmarks/pldi2026/btree/5o2u.wat | 2 +- benchmarks/pldi2026/btree/5o3u.wat | 2 +- benchmarks/pldi2026/btree/6o1u.wat | 2 +- benchmarks/pldi2026/btree/6o2u.wat | 2 +- benchmarks/pldi2026/btree/6o3u.wat | 2 +- benchmarks/pldi2026/btree/7o1u.wat | 2 +- benchmarks/pldi2026/btree/7o2u.wat | 2 +- benchmarks/pldi2026/btree/7o3u.wat | 2 +- benchmarks/pldi2026/btree/8o1u.wat | 2 +- benchmarks/pldi2026/btree/9o1u.wat | 2 +- benchmarks/pldi2026/btree/9o2u.wat | 2 +- 20 files changed, 20 insertions(+), 20 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o1u.wat b/benchmarks/pldi2026/btree/2o1u.wat index 99f628164..e23c8fe1b 100644 --- a/benchmarks/pldi2026/btree/2o1u.wat +++ b/benchmarks/pldi2026/btree/2o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 9922fcc42..49f245e67 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index 5f8232df6..6fd718aa5 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index ec97e5903..605bb81fa 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index 60d0483be..b67fd27eb 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index 6dfc71a31..c74466b53 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 4beac7a48..0c0966990 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index 1fac09846..dc2a36e6b 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 1ef41296a..0a4ff6840 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 432244e36..51775f0ea 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index 058891947..c18b66f62 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index 7302e3507..1d55287bf 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 8c22aa9c1..804c345fb 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index ee7d08bb5..b4fc26a78 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index 576560feb..e865bc50f 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index d8c85450a..2169d6064 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 0f7fd87aa..16057c8c8 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 9f76c0a17..3af9992f7 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index 8686ccde9..e82594580 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index fff6815d5..ba0affca7 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 From b6056d8be41c095118f72dd70e63ddefb9debc33 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 22:34:22 -0400 Subject: [PATCH 067/105] take get_sym_int32 back but don't use them --- benchmarks/pldi2026/btree/2o1u.wat | 2 +- benchmarks/pldi2026/btree/2o2u.wat | 2 +- benchmarks/pldi2026/btree/3o1u.wat | 2 +- benchmarks/pldi2026/btree/3o2u.wat | 2 +- benchmarks/pldi2026/btree/3o3u.wat | 2 +- benchmarks/pldi2026/btree/4o1u.wat | 2 +- benchmarks/pldi2026/btree/4o2u.wat | 2 +- benchmarks/pldi2026/btree/4o3u.wat | 2 +- benchmarks/pldi2026/btree/5o1u.wat | 2 +- benchmarks/pldi2026/btree/5o2u.wat | 2 +- benchmarks/pldi2026/btree/5o3u.wat | 2 +- benchmarks/pldi2026/btree/6o1u.wat | 2 +- benchmarks/pldi2026/btree/6o2u.wat | 2 +- benchmarks/pldi2026/btree/6o3u.wat | 2 +- benchmarks/pldi2026/btree/7o1u.wat | 2 +- benchmarks/pldi2026/btree/7o2u.wat | 2 +- benchmarks/pldi2026/btree/7o3u.wat | 2 +- benchmarks/pldi2026/btree/8o1u.wat | 2 +- benchmarks/pldi2026/btree/9o1u.wat | 2 +- benchmarks/pldi2026/btree/9o2u.wat | 2 +- 20 files changed, 20 insertions(+), 20 deletions(-) diff --git a/benchmarks/pldi2026/btree/2o1u.wat b/benchmarks/pldi2026/btree/2o1u.wat index e23c8fe1b..99f628164 100644 --- a/benchmarks/pldi2026/btree/2o1u.wat +++ b/benchmarks/pldi2026/btree/2o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/2o2u.wat b/benchmarks/pldi2026/btree/2o2u.wat index 49f245e67..9922fcc42 100644 --- a/benchmarks/pldi2026/btree/2o2u.wat +++ b/benchmarks/pldi2026/btree/2o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o1u.wat b/benchmarks/pldi2026/btree/3o1u.wat index 6fd718aa5..5f8232df6 100644 --- a/benchmarks/pldi2026/btree/3o1u.wat +++ b/benchmarks/pldi2026/btree/3o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o2u.wat b/benchmarks/pldi2026/btree/3o2u.wat index 605bb81fa..ec97e5903 100644 --- a/benchmarks/pldi2026/btree/3o2u.wat +++ b/benchmarks/pldi2026/btree/3o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/3o3u.wat b/benchmarks/pldi2026/btree/3o3u.wat index b67fd27eb..60d0483be 100644 --- a/benchmarks/pldi2026/btree/3o3u.wat +++ b/benchmarks/pldi2026/btree/3o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o1u.wat b/benchmarks/pldi2026/btree/4o1u.wat index c74466b53..6dfc71a31 100644 --- a/benchmarks/pldi2026/btree/4o1u.wat +++ b/benchmarks/pldi2026/btree/4o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o2u.wat b/benchmarks/pldi2026/btree/4o2u.wat index 0c0966990..4beac7a48 100644 --- a/benchmarks/pldi2026/btree/4o2u.wat +++ b/benchmarks/pldi2026/btree/4o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/4o3u.wat b/benchmarks/pldi2026/btree/4o3u.wat index dc2a36e6b..1fac09846 100644 --- a/benchmarks/pldi2026/btree/4o3u.wat +++ b/benchmarks/pldi2026/btree/4o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o1u.wat b/benchmarks/pldi2026/btree/5o1u.wat index 0a4ff6840..1ef41296a 100644 --- a/benchmarks/pldi2026/btree/5o1u.wat +++ b/benchmarks/pldi2026/btree/5o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o2u.wat b/benchmarks/pldi2026/btree/5o2u.wat index 51775f0ea..432244e36 100644 --- a/benchmarks/pldi2026/btree/5o2u.wat +++ b/benchmarks/pldi2026/btree/5o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/5o3u.wat b/benchmarks/pldi2026/btree/5o3u.wat index c18b66f62..058891947 100644 --- a/benchmarks/pldi2026/btree/5o3u.wat +++ b/benchmarks/pldi2026/btree/5o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o1u.wat b/benchmarks/pldi2026/btree/6o1u.wat index 1d55287bf..7302e3507 100644 --- a/benchmarks/pldi2026/btree/6o1u.wat +++ b/benchmarks/pldi2026/btree/6o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o2u.wat b/benchmarks/pldi2026/btree/6o2u.wat index 804c345fb..8c22aa9c1 100644 --- a/benchmarks/pldi2026/btree/6o2u.wat +++ b/benchmarks/pldi2026/btree/6o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/6o3u.wat b/benchmarks/pldi2026/btree/6o3u.wat index b4fc26a78..ee7d08bb5 100644 --- a/benchmarks/pldi2026/btree/6o3u.wat +++ b/benchmarks/pldi2026/btree/6o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o1u.wat b/benchmarks/pldi2026/btree/7o1u.wat index e865bc50f..576560feb 100644 --- a/benchmarks/pldi2026/btree/7o1u.wat +++ b/benchmarks/pldi2026/btree/7o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o2u.wat b/benchmarks/pldi2026/btree/7o2u.wat index 2169d6064..d8c85450a 100644 --- a/benchmarks/pldi2026/btree/7o2u.wat +++ b/benchmarks/pldi2026/btree/7o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/7o3u.wat b/benchmarks/pldi2026/btree/7o3u.wat index 16057c8c8..0f7fd87aa 100644 --- a/benchmarks/pldi2026/btree/7o3u.wat +++ b/benchmarks/pldi2026/btree/7o3u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/8o1u.wat b/benchmarks/pldi2026/btree/8o1u.wat index 3af9992f7..9f76c0a17 100644 --- a/benchmarks/pldi2026/btree/8o1u.wat +++ b/benchmarks/pldi2026/btree/8o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/9o1u.wat b/benchmarks/pldi2026/btree/9o1u.wat index e82594580..8686ccde9 100644 --- a/benchmarks/pldi2026/btree/9o1u.wat +++ b/benchmarks/pldi2026/btree/9o1u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 diff --git a/benchmarks/pldi2026/btree/9o2u.wat b/benchmarks/pldi2026/btree/9o2u.wat index ba0affca7..fff6815d5 100644 --- a/benchmarks/pldi2026/btree/9o2u.wat +++ b/benchmarks/pldi2026/btree/9o2u.wat @@ -7,7 +7,7 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - ;; (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func (;4;) (type 0) (param i32) (result i32) i32.const 0 local.get 0 From f51290d863ab0a4f15f42f3983c5267437b1b0dd Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 22:53:56 -0400 Subject: [PATCH 068/105] a test entry that compile btree cases --- .../scala/wasm/StagedConcolicMiniWasm.scala | 35 ++++++++--- .../scala/genwasym/TestBenchmarkBtree.scala | 63 +++++++++++++++++++ 2 files changed, 88 insertions(+), 10 deletions(-) create mode 100644 src/test/scala/genwasym/TestBenchmarkBtree.scala diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index cafddbf0b..b6e830d46 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -152,6 +152,21 @@ trait StagedWasmEvaluator extends SAIOps { () } + def evalSymbolic(ty: ValueType, + rest: List[Instr], + kont: Context => Rep[Cont[Unit]], + mkont: Rep[MCont[Unit]], + trail: Trail[Unit])(implicit ctx: Context) = { + Stack.popC(ty) + val id = Stack.popS(ty) + val symVal = id.makeSymbolic(ty) + val num = SymEnv.read(symVal.s) + Stack.pushC(StagedConcreteNum(ty, num)) + Stack.pushS(symVal) + val newCtx = ctx.pop()._2.push(ty) + eval(rest, kont, mkont, trail)(newCtx) + } + def eval(insts: List[Instr], kont: Context => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], @@ -174,15 +189,7 @@ trait StagedWasmEvaluator extends SAIOps { Stack.pushS(toStagedSymbolicNum(num)) val newCtx = ctx.push(num.tipe(module)) eval(rest, kont, mkont, trail)(newCtx) - case Symbolic(ty) => - Stack.popC(ty) - val id = Stack.popS(ty) - val symVal = id.makeSymbolic(ty) - val num = SymEnv.read(symVal.s) - Stack.pushC(StagedConcreteNum(ty, num)) - Stack.pushS(symVal) - val newCtx = ctx.pop()._2.push(ty) - eval(rest, kont, mkont, trail)(newCtx) + case Symbolic(ty) => evalSymbolic(ty, rest, kont, mkont, trail)(ctx) case LocalGet(i) => Stack.pushC(Frames.getC(i)) Stack.pushS(Frames.getS(i)) @@ -530,7 +537,15 @@ trait StagedWasmEvaluator extends SAIOps { val s = Stack.popS(ty) runtimeAssert(v.toInt != 0) eval(rest, kont, mkont, trail)(newCtx) - case Import(_, _, _) => throw new Exception(s"Unknown import at $funcIndex") + case Import("i32", "symbolic", _) => + evalSymbolic(NumType(I32Type), rest, kont, mkont, trail)(ctx) + case Import("i32", "sym_assume", _) => + // TODO: implement sym_assume + eval(rest, kont, mkont, trail)(ctx.pop()._2) + case Import("i32", "sym_assert", _) => + // TODO: implement sym_assert + eval(rest, kont, mkont, trail)(ctx.pop()._2) + case Import(m, f, _) => throw new Exception(s"Unknown import $m.$f at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } } diff --git a/src/test/scala/genwasym/TestBenchmarkBtree.scala b/src/test/scala/genwasym/TestBenchmarkBtree.scala new file mode 100644 index 000000000..edec49759 --- /dev/null +++ b/src/test/scala/genwasym/TestBenchmarkBtree.scala @@ -0,0 +1,63 @@ +package gensym.wasm + +import org.scalatest.FunSuite + +import lms.core.stub.Adapter + +import gensym.wasm.miniwasm.{ModuleInstance} +import gensym.wasm.parser._ +import gensym.wasm.stagedconcolicminiwasm._ + +// This 'test file' is not intended to test functionality, but to generate compiled code for btree benchmarks +class TestBenchmarkBtree extends FunSuite { + def compileToCpp(filename: String, + main: Option[String] = None) = { + import sys.process._ + + println(s"Compiling $filename to C++") + val moduleInst = ModuleInstance(Parser.parseFile(filename)) + val cppFile = s"$filename.cpp" + val generated = WasmToCppCompiler.compile(moduleInst, main, false) + + val code = generated.source + val writer = new java.io.PrintWriter(new java.io.File(cppFile)) + try { + writer.write(code) + } finally { + writer.close() + } + } + + def compileDirToCpp(dir: String, + main: Option[String] = None) = { + import java.io.File + val d = new File(dir) + d.listFiles().filter(_.getName.endsWith(".wat")).foreach { file => + compileToCpp(file.getAbsolutePath, main) + } + } + + // only test concrete execution and its result + def testFileConcreteCpp(filename: String, main: Option[String] = None, expect: Option[List[Float]] = None) = { + val moduleInst = ModuleInstance(Parser.parseFile(filename)) + val cppFile = s"$filename.cpp" + val exe = s"$cppFile.exe" + WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, "NO_INFO", "RUN_ONCE", "USE_IMM") + + import sys.process._ + val result = s"./$exe".!! + println(result) + + expect.map(vs => { + val stackValues = result + .split("Stack contents: \n")(1) + .split("\n") + .map(_.toFloat) + .toList + assert(vs == stackValues) + }) + } + + test("compile-btree-benchmarks") { compileDirToCpp("./benchmarks/pldi2026/btree/", Some("main")) } + +} From 832af8b5219144777f2fef0ba632ecf226e699d7 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 28 Oct 2025 23:08:27 -0400 Subject: [PATCH 069/105] a compile script in python --- benchmarks/pldi2026/btree/compile.py | 74 ++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 benchmarks/pldi2026/btree/compile.py diff --git a/benchmarks/pldi2026/btree/compile.py b/benchmarks/pldi2026/btree/compile.py new file mode 100644 index 000000000..af98295d4 --- /dev/null +++ b/benchmarks/pldi2026/btree/compile.py @@ -0,0 +1,74 @@ +import sys +import subprocess +from pathlib import Path + +#!/usr/bin/env python3 + +# Compile all .cpp files in this script's directory into executables with the same stem. +# Usage: python compile.py [extra g++ flags...] + +HERE = Path(__file__).resolve().parent +CPP_FILES = sorted(HERE.glob("*.cpp")) + +if not CPP_FILES: + print(f"No .cpp files found in {HERE}") + sys.exit(0) + +DEFAULT_FLAGS = [ + "-std=c++17", + "-g", + "-O0", + "-Wall", + "-Wextra", + "-DUSE_IMM", + "-I/home/zdh/WorkSpace/GenSym/headers", + "-lz3", + "-DENABLE_PROFILE_TIME", + "-DNO_REUSE", +] +EXTRA_FLAGS = sys.argv[1:] +FLAGS = DEFAULT_FLAGS + EXTRA_FLAGS + + +def compile_all(cpp_files=None, flags=None): + if cpp_files is None: + cpp_files = CPP_FILES + if flags is None: + flags = FLAGS + + compiled_total = 0 + compiled_success = 0 + compiled_failed = 0 + + for cpp in cpp_files: + out = cpp.with_suffix(".exe") # foo.cpp -> ./foo + cmd = ["g++", str(cpp), "-o", str(out)] + flags + print("Compiling:", cpp.name) + try: + proc = subprocess.run(cmd, capture_output=True, text=True) + except FileNotFoundError: + print("Error: g++ not found. Install a C++ compiler.") + sys.exit(1) + + compiled_total += 1 + if proc.returncode == 0: + compiled_success += 1 + print(" -> OK:", out.name) + else: + compiled_failed += 1 + print(" -> FAILED:", cpp.name) + if proc.stdout: + print(proc.stdout.strip()) + if proc.stderr: + print(proc.stderr.strip()) + + print() + print("Overall summary:") + print(f" Files compiled: {compiled_total}") + print(f" Succeeded: {compiled_success}") + print(f" Failed: {compiled_failed}") + return compiled_total, compiled_success, compiled_failed + + +if __name__ == "__main__": + compile_all() From 94fe90109801d96a4cbd9121c20460c0ab23df2b Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 29 Oct 2025 21:49:31 -0400 Subject: [PATCH 070/105] avoid some usage of fun --- headers/wasm/controls.hpp | 50 ++++++++++++++++++- .../scala/wasm/StagedConcolicMiniWasm.scala | 38 +++++++++----- 2 files changed, 75 insertions(+), 13 deletions(-) diff --git a/headers/wasm/controls.hpp b/headers/wasm/controls.hpp index 97ba0130f..ae0997828 100644 --- a/headers/wasm/controls.hpp +++ b/headers/wasm/controls.hpp @@ -4,10 +4,58 @@ #include +#include +#include #include -using MCont_t = std::function; +class MContRepr; +struct MCont_t { + std::shared_ptr ptr; + MCont_t() : ptr(nullptr) {} + MCont_t(const MCont_t &p) : ptr(p.ptr) {} + MCont_t(std::shared_ptr p) : ptr(p) {} + MCont_t(std::function haltK) + : ptr(std::make_shared(haltK)) {} + bool is_null() const { return ptr == nullptr; } + + std::monostate enter(); +}; using Cont_t = std::function; +class MContRepr { +public: + MContRepr(Cont_t cont, MCont_t mcont) : cont(cont), mcont(mcont) {} + + MContRepr(std::function haltK) + : cont([=](MCont_t) { + // std::cout << "Halting the program..." << std::endl; + + return haltK(std::monostate{}); + }), + mcont() {} + + MContRepr() : cont(nullptr), mcont() {} + + std::monostate enter() { + // std::cout << "Entering MCont\n"; + // std::cout << "Cont cont: " << (cont ? "valid" : "null") << "\n"; + // std::cout << "MCont mcont: " << (mcont ? "valid" : "null") << "\n"; + if (mcont.is_null()) { + return cont(std::make_shared( + MContRepr())); // when mcont is null, we pass a dummy MContRepr + } + return cont(mcont); + } + +private: + Cont_t cont; + MCont_t mcont; +}; + +inline MCont_t prependCont(Cont_t k, MCont_t mcont) { + return std::make_shared(k, mcont); +} + +inline std::monostate MCont_t::enter() { return ptr->enter(); } struct Control { Cont_t cont; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index b6e830d46..ec91e94f3 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -119,15 +119,13 @@ trait StagedWasmEvaluator extends SAIOps { } } - type MCont[A] = Unit => A + class MCont[A] type Cont[A] = (MCont[A]) => A type Trail[A] = List[Context => Rep[Cont[A]]] // a cache storing the compiled code for each function, to reduce re-compilation val compileCache = new HashMap[Int, Rep[(MCont[Unit]) => Unit]] - def makeDummy: Rep[Unit] = "dummy".reflectCtrlWith[Unit]() - def funHere[A:Manifest,B:Manifest](f: Rep[A] => Rep[B], dummy: Rep[Unit]): Rep[A => B] = { // to avoid LMS lifting a function, we create a dummy node and read it inside function fun((x: Rep[A]) => { @@ -136,6 +134,20 @@ trait StagedWasmEvaluator extends SAIOps { }) } + def makeInitMCont[A:Manifest](f: Rep[Unit => A]): Rep[MCont[A]] = { + "make-init-mcont".reflectCtrlWith[MCont[A]](f) + } + + implicit class MContOps[A:Manifest](mk: Rep[MCont[A]]) { + def prependCont(k: Rep[Cont[A]]): Rep[MCont[A]] = { + "mcont-prepend".reflectCtrlWith[MCont[A]](mk, k) + } + + def enter(): Rep[A] = { + "mcont-enter".reflectCtrlWith[A](mk) + } + } + trait Control // Save the current control information into a structure Control @@ -308,7 +320,6 @@ trait StagedWasmEvaluator extends SAIOps { // the type system guarantees that we will never take more than the input size from the stack val funcTy = ty.funcType val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size - val dummy = makeDummy def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the block, stackSize =", Stack.size) val offset = restCtx.stackTypes.size - exitSize @@ -321,7 +332,6 @@ trait StagedWasmEvaluator extends SAIOps { case Loop(ty, inner) => val funcTy = ty.funcType val exitSize = ctx.stackTypes.size - funcTy.inps.size + funcTy.out.size - val dummy = makeDummy def restK(restCtx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the loop, stackSize =", Stack.size) val offset = restCtx.stackTypes.size - exitSize @@ -454,7 +464,7 @@ trait StagedWasmEvaluator extends SAIOps { } } - def forwardKont: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => mk(())) + def forwardKont: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => mk.enter()) def evalCall(rest: List[Instr], @@ -481,7 +491,7 @@ trait StagedWasmEvaluator extends SAIOps { val offset = ctx.stackTypes.size - ty.out.size Stack.shiftC(offset, ty.out.size) Stack.shiftS(offset, ty.out.size) - mk(()) + mk.enter() }) eval(body, retK _, mk, retK _::Nil)(Context(Nil, locals)) }) @@ -510,10 +520,7 @@ trait StagedWasmEvaluator extends SAIOps { Frames.popFrameS(locals.size) eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) }) - val dummy = makeDummy - val newMKont: Rep[MCont[Unit]] = funHere((_u: Rep[Unit]) => { - restK(mkont) - }, dummy) + val newMKont: Rep[MCont[Unit]] = mkont.prependCont(restK) Frames.pushFrameC(locals) Frames.pushFrameS(locals) Frames.putAllC(argsC) @@ -672,7 +679,7 @@ trait StagedWasmEvaluator extends SAIOps { ExploreTree.fillWithFinished() "no-op".reflectCtrlWith[Unit]() } - val temp: Rep[MCont[Unit]] = topFun(haltK) + val temp: Rep[MCont[Unit]] = makeInitMCont(topFun(haltK)) evalTop(temp, main) } @@ -1356,6 +1363,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { else if (m.toString.endsWith("I64V")) "I64V" else if (m.toString.endsWith("SymVal")) "SymVal" else if (m.toString.endsWith("Snapshot")) "Snapshot_t" + else if (m.toString.endsWith("MCont[Unit]")) "MCont_t" else super.remap(m) } @@ -1547,6 +1555,12 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("ExploreTree.dump_graphviz("); shallow(f); emit(")") case Node(_, "sym-not", List(s), _) => shallow(s); emit(".negate()") + case Node(_, "make-init-mcont", List(haltK), _) => + emit("MCont_t("); shallow(haltK); emit(")") + case Node(_, "mcont-prepend", List(mkont, kont), _) => + emit("prependCont("); shallow(kont); emit(", "); shallow(mkont); emit(")") + case Node(_, "mcont-enter", List(mkont), _) => + shallow(mkont); emit(".enter()") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => From ae49b39807f3366798fcd6e15966050753c18502 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 29 Oct 2025 21:57:30 -0400 Subject: [PATCH 071/105] remove an unused function --- .../scala/genwasym/TestBenchmarkBtree.scala | 21 ------------------- 1 file changed, 21 deletions(-) diff --git a/src/test/scala/genwasym/TestBenchmarkBtree.scala b/src/test/scala/genwasym/TestBenchmarkBtree.scala index edec49759..8e9bc0c29 100644 --- a/src/test/scala/genwasym/TestBenchmarkBtree.scala +++ b/src/test/scala/genwasym/TestBenchmarkBtree.scala @@ -37,27 +37,6 @@ class TestBenchmarkBtree extends FunSuite { } } - // only test concrete execution and its result - def testFileConcreteCpp(filename: String, main: Option[String] = None, expect: Option[List[Float]] = None) = { - val moduleInst = ModuleInstance(Parser.parseFile(filename)) - val cppFile = s"$filename.cpp" - val exe = s"$cppFile.exe" - WasmToCppCompiler.compileToExe(moduleInst, main, cppFile, exe, true, optimizeLevel=0, "NO_INFO", "RUN_ONCE", "USE_IMM") - - import sys.process._ - val result = s"./$exe".!! - println(result) - - expect.map(vs => { - val stackValues = result - .split("Stack contents: \n")(1) - .split("\n") - .map(_.toFloat) - .toList - assert(vs == stackValues) - }) - } - test("compile-btree-benchmarks") { compileDirToCpp("./benchmarks/pldi2026/btree/", Some("main")) } } From 2e568515d4a9e63defa9c045c2117bb3e1f1cb3a Mon Sep 17 00:00:00 2001 From: ahuoguo Date: Fri, 31 Oct 2025 11:33:42 -0400 Subject: [PATCH 072/105] nontermination (if loop termination depends on symbolic value, it will explode the user's stack instead, now it gets out of bounds for the concrete stack in c++) --- benchmarks/wasm/diverge.wat | 33 +++++++++++++++++++ .../genwasym/TestStagedConcolicEval.scala | 5 +++ 2 files changed, 38 insertions(+) create mode 100644 benchmarks/wasm/diverge.wat diff --git a/benchmarks/wasm/diverge.wat b/benchmarks/wasm/diverge.wat new file mode 100644 index 000000000..8de7dcc1d --- /dev/null +++ b/benchmarks/wasm/diverge.wat @@ -0,0 +1,33 @@ +(module $diverge + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32))) + (import "console" "assert" (func (;0;) (type 2))) + (import "console" "log" (func (;1;) (type 2))) + ;; f x = if x == 0 then 42 else f x + (func (;2;) (type 0) (param i32) (result i32) + local.get 0 + i32.const 0 + i32.eq + if (result i32) + i32.const 42 + else + local.get 0 + call 1 + local.get 0 + call 2 + i32.const 0 + call 0 + unreachable + end + ) + (func $real_main (;2;) (type 1) + i32.const 0 + i32.symbolic + call 2 + drop + ) + (start 3) + (export "main" (func 3)) + +) \ No newline at end of file diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 86f55daa2..d1590f6a0 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -178,4 +178,9 @@ class TestStagedConcolicEval extends FunSuite { test("small-snapshot-concrete") { testFileConcreteCpp("./benchmarks/wasm/compare_wasp/small-snapshot.wat", Some("main")) } + + // test("diverge") { + // testFileConcolicCpp("./benchmarks/wasm/diverge.wat", Some("main")) + // } + } From c8e629f54c0f1bb20866ad3ea09e4d2f8daf3ca6 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 3 Nov 2025 14:19:22 -0500 Subject: [PATCH 073/105] support sym_assume to prune subtrees --- headers/wasm/concolic_driver.hpp | 3 +- headers/wasm/symbolic_rt.hpp | 94 ++++++++++++++++++- .../scala/wasm/StagedConcolicMiniWasm.scala | 45 ++++++++- 3 files changed, 137 insertions(+), 5 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 80ff38d5f..2a9a994d0 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -48,7 +48,7 @@ class ManagedConcolicCleanup { if (driver.tree_file.has_value()) ExploreTree.dump_graphviz(driver.tree_file.value()); - // Clear the symbol bookkeeper + // Clear the symbol bookkeeper SymBookKeeper.clear(); } }; @@ -134,6 +134,7 @@ inline void ConcolicDriver::main_exploration_loop() { inline void ConcolicDriver::run() { main_exploration_loop(); + ExploreTree.print_overall_result(); Profile.print_summary(); } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 6edef6ee8..2bcfe7aca 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -543,6 +543,7 @@ struct NodeBox { std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); std::monostate fillSnapshotNode(Snapshot_t snapshot); + std::monostate fillNotToExploreNode(); bool isUnexplored() const; std::vector collect_path_conds(); int min_cost_of_reaching_here(); @@ -664,6 +665,22 @@ struct UnExploredNode : Node { } }; +struct NotToExploreNode : Node { + NotToExploreNode() {} + std::string to_string() override { return "NotToExploreNode"; } + +protected: + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id++; + graphviz_node(os, current_node_dot_id, "NotToExplore", "box", "grey"); + + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } + } +}; + struct SnapshotNode : Node { SnapshotNode(Snapshot_t snapshot) : snapshot(snapshot) {} std::string to_string() override { return "SnapshotNode"; } @@ -761,6 +778,15 @@ inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { return std::monostate(); } +inline std::monostate NodeBox::fillNotToExploreNode() { + if (this->isUnexplored()) { + node = std::make_unique(); + } else { + assert(dynamic_cast(node.get()) != nullptr); + } + return std::monostate(); +} + inline std::monostate NodeBox::fillFinishedNode() { if (this->isUnexplored()) { node = std::make_unique(); @@ -896,6 +922,10 @@ class ExploreTree_t { return std::monostate(); } + std::monostate fillNotToExploredNode() { + return cursor->fillNotToExploreNode(); + } + bool worth_to_create_snapshot() { if (!ENABLE_COST_MODEL) { return REUSE_SNAPSHOT; @@ -911,8 +941,8 @@ class ExploreTree_t { auto parent_cost = cursor->parent ? cursor->parent->min_cost_of_reaching_here() : 0; auto exec_from_parent_cost = reach_parent_cost + cursor->instr_cost; - GENSYM_INFO("The score of snapshot tendency: " + std::to_string(exec_from_parent_cost - - snapshot_cost)); + GENSYM_INFO("The score of snapshot tendency: " + + std::to_string(exec_from_parent_cost - snapshot_cost)); return snapshot_cost <= exec_from_parent_cost; } @@ -924,6 +954,7 @@ class ExploreTree_t { if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); int cost_from_parent = CostManager.dump_instr_cost(); + cursor->instr_cost = cost_from_parent; if (branch) { true_branch_cov_map[if_else_node->id] = true; if (worth_to_create_snapshot()) { @@ -947,6 +978,26 @@ class ExploreTree_t { return std::monostate(); } + std::monostate moveCursorNoControl(bool branch) { + Profile.step(StepProfileKind::CURSOR_MOVE); + assert(cursor != nullptr); + auto if_else_node = dynamic_cast(cursor->node.get()); + assert( + if_else_node != nullptr && + "Can't move cursor when the branch node is not initialized correctly!"); + int cost_from_parent = CostManager.dump_instr_cost(); + cursor->instr_cost = cost_from_parent; + if (branch) { + true_branch_cov_map[if_else_node->id] = true; + if_else_node->false_branch->fillNotToExploreNode(); + cursor = if_else_node->true_branch.get(); + } else { + assert(false && + "moveCursorNoControl should not be used for false branch"); + } + return std::monostate(); + } + std::monostate print() { std::cout << root->node->to_string() << std::endl; return std::monostate(); @@ -966,6 +1017,45 @@ class ExploreTree_t { return std::monostate(); } + std::monostate print_overall_result() { + // Print how many paths have been explored, how many paths are unreachable, + // how many paths are failed, how many paths are finished successfully + int unexplored_count = 0; + int finished_count = 0; + int failed_count = 0; + int not_to_explore_count = 0; + int unreachable_count = 0; + std::function dfs = [&](NodeBox *node) { + if (auto if_else_node = dynamic_cast(node->node.get())) { + dfs(if_else_node->true_branch.get()); + dfs(if_else_node->false_branch.get()); + } else if (dynamic_cast(node->node.get())) { + unexplored_count += 1; + } else if (dynamic_cast(node->node.get())) { + finished_count += 1; + } else if (dynamic_cast(node->node.get())) { + failed_count += 1; + } else if (dynamic_cast(node->node.get())) { + unreachable_count += 1; + } else if (dynamic_cast(node->node.get())) { + // Snapshot node is considered unexplored + unexplored_count += 1; + } else if (dynamic_cast(node->node.get())) { + not_to_explore_count += 1; + } else { + throw std::runtime_error("Unknown node type in explore tree"); + } + }; + dfs(root.get()); + std::cout << "Explore Tree Overall Result:" << std::endl; + std::cout << " Unexplored paths: " << unexplored_count << std::endl; + std::cout << " Finished paths: " << finished_count << std::endl; + std::cout << " Failed paths: " << failed_count << std::endl; + std::cout << " Unreachable paths: " << unreachable_count << std::endl; + std::cout << " NotToExplore paths: " << not_to_explore_count << std::endl; + return std::monostate(); + } + NodeBox *pick_unexplored() { // Pick an unexplored node from the tree // For now, we just iterate through the tree and return the first unexplored diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index ec91e94f3..308ce55a4 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -31,6 +31,12 @@ object Counter { dict.clear() } + def getId(): Int = { + val id = currentId + currentId += 1 + id + } + def getId(wir: WIR, nth: Int = 0): Int = { if (dict.contains((wir, nth))) { dict((wir, nth)) @@ -547,8 +553,28 @@ trait StagedWasmEvaluator extends SAIOps { case Import("i32", "symbolic", _) => evalSymbolic(NumType(I32Type), rest, kont, mkont, trail)(ctx) case Import("i32", "sym_assume", _) => - // TODO: implement sym_assume - eval(rest, kont, mkont, trail)(ctx.pop()._2) + // symbolic assume is just like an if else that only has one branch, while another + // is marked as not-to-explore + val (condTy, newCtx) = ctx.pop() + Predef.assert(condTy == NumType(I32Type), s"sym_assume only supports i32 condition, get $condTy") + val cond = Stack.popC(condTy) + val symCond = Stack.popS(condTy) + val id = Counter.getId() + ExploreTree.fillWithIfElse(symCond.s, id) + def thnK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Successfully assumed condition at $id") + eval(rest, kont, mk, trail)(newCtx) + }) + if (cond.toInt != 0) { + ExploreTree.moveCursor(true) + eval(rest, kont, mkont, trail)(newCtx) + } else { + val control = makeControl(thnK, mkont) + ExploreTree.moveCursor(false, control) + // just stop the execution at here + ExploreTree.fillWithNotToExplore() + } + () case Import("i32", "sym_assert", _) => // TODO: implement sym_assert eval(rest, kont, mkont, trail)(ctx.pop()._2) @@ -637,6 +663,8 @@ trait StagedWasmEvaluator extends SAIOps { def evalTop(mkont: Rep[MCont[Unit]], main: Option[String]): Rep[Unit] = { Counter.reset() + Predef.println("[DEBUG]" + module) + Predef.println("[DEBUG] module.defs: " + module.defs) val funBody: FuncBodyDef = main match { case Some(func_name) => module.defs.flatMap({ @@ -889,6 +917,10 @@ trait StagedWasmEvaluator extends SAIOps { "tree-fill-if-else".reflectCtrlWith[Unit](s, id) } + def fillWithNotToExplore(): Rep[Unit] = { + "tree-fill-not-to-explore".reflectCtrlWith[Unit]() + } + def fillWithFinished(): Rep[Unit] = { "tree-fill-finished".reflectCtrlWith[Unit]() } @@ -898,6 +930,11 @@ trait StagedWasmEvaluator extends SAIOps { "tree-move-cursor".reflectCtrlWith[Unit](branch, control) } + def moveCursor(branch: Boolean): Rep[Unit] = { + // when moving cursor from to an unexplored node, we need to change the reuse state + "tree-move-cursor-no-control".reflectCtrlWith[Unit](branch) + } + def print(): Rep[Unit] = { "tree-print".reflectCtrlWith[Unit]() } @@ -1543,10 +1580,14 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("GENSYM_ASSERT("); shallow(cond); emit(")") case Node(_, "tree-fill-if-else", List(sym, id), _) => emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(", "); emit(id.toString); emit(")") + case Node(_, "tree-fill-not-to-explore", List(), _) => + emit("ExploreTree.fillNotToExploredNode()") case Node(_, "tree-fill-finished", List(), _) => emit("ExploreTree.fillFinishedNode()") case Node(_, "tree-move-cursor", List(b, snapshot), _) => emit("ExploreTree.moveCursor("); shallow(b); emit(", "); shallow(snapshot); emit(")") + case Node(_, "tree-move-cursor-no-control", List(b), _) => + emit("ExploreTree.moveCursorNoControl("); shallow(b); emit(")") case Node(_, "add-instr-cost", List(n), _) => emit("CostManager.add_instr_cost("); shallow(n); emit(")") case Node(_, "tree-print", List(), _) => From 2ced35434d68be1cc139ab6f315ab367d861787a Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 3 Nov 2025 15:20:00 -0500 Subject: [PATCH 074/105] support write profile file --- benchmarks/pldi2026/btree/compile.py | 2 + headers/wasm/concolic_driver.hpp | 7 +++- headers/wasm/output_report.hpp | 54 ++++++++++++++++++++++++ headers/wasm/profile.hpp | 60 ++++++++++++++++++++++++++- headers/wasm/symbolic_rt.hpp | 61 ++++++++++++++++++---------- 5 files changed, 160 insertions(+), 24 deletions(-) create mode 100644 headers/wasm/output_report.hpp diff --git a/benchmarks/pldi2026/btree/compile.py b/benchmarks/pldi2026/btree/compile.py index af98295d4..8c0b53722 100644 --- a/benchmarks/pldi2026/btree/compile.py +++ b/benchmarks/pldi2026/btree/compile.py @@ -45,6 +45,8 @@ def compile_all(cpp_files=None, flags=None): cmd = ["g++", str(cpp), "-o", str(out)] + flags print("Compiling:", cpp.name) try: + print(" Executing command:") + print(" ", " ".join(cmd)) proc = subprocess.run(cmd, capture_output=True, text=True) except FileNotFoundError: print("Error: g++ not found. Install a C++ compiler.") diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 2a9a994d0..e13e58824 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -7,6 +7,7 @@ #include "smt_solver.hpp" #include "symbolic_rt.hpp" #include "utils.hpp" +#include "output_report.hpp" #include #include #include @@ -48,7 +49,7 @@ class ManagedConcolicCleanup { if (driver.tree_file.has_value()) ExploreTree.dump_graphviz(driver.tree_file.value()); - // Clear the symbol bookkeeper + // Clear the symbol bookkeeper SymBookKeeper.clear(); } }; @@ -134,8 +135,10 @@ inline void ConcolicDriver::main_exploration_loop() { inline void ConcolicDriver::run() { main_exploration_loop(); - ExploreTree.print_overall_result(); + auto overall = ExploreTree.read_current_overall_result(); + overall.print(); Profile.print_summary(); + dump_all_summary_json(Profile, overall); } static void start_concolic_execution_with( diff --git a/headers/wasm/output_report.hpp b/headers/wasm/output_report.hpp new file mode 100644 index 000000000..a1a08f0b7 --- /dev/null +++ b/headers/wasm/output_report.hpp @@ -0,0 +1,54 @@ +#ifndef WASM_OUTPUT_REPORT_HPP +#define WASM_OUTPUT_REPORT_HPP + +#include "profile.hpp" +#include "symbolic_rt.hpp" +#include "config.hpp" +#include + +inline void dump_all_summary_json(const Profile_t &profile, + const OverallResult &overall) { + // use environment variable OUTPUT_DIR to config particular output directory + // use environment variable OUTPUT_DIR to config particular output directory + const char *output_dir = std::getenv("OUTPUT_DIR"); + if (output_dir == nullptr) { + return; + } + + std::filesystem::path outdir(output_dir); + + std::filesystem::path report_path = + outdir / std::filesystem::path("concolic_execution_report.json"); + + auto parent = report_path.parent_path(); + if (!parent.empty()) { + std::error_code ec; + std::filesystem::create_directories(parent, ec); + if (ec) { + throw std::runtime_error("Failed to create output directory: " + + ec.message()); + } + } + + std::ofstream ofs(report_path); + if (!ofs.is_open()) { + throw std::runtime_error("Failed to open " + report_path.string() + + " for writing"); + } + + // Simple JSON dump (pretty-printed) + ofs << "{\n"; + ofs << " \"unexplored_count\": " << overall.unexplored_count << ",\n"; + ofs << " \"finished_count\": " << overall.finished_count << ",\n"; + ofs << " \"failed_count\": " << overall.failed_count << ",\n"; + ofs << " \"not_to_explore_count\": " << overall.not_to_explore_count + << ",\n"; + ofs << " \"unreachable_count\": " << overall.unreachable_count; + if (PROFILE_STEP || PROFILE_TIME) { + ofs << ",\n"; + profile.write_as_json(ofs); + } + ofs << "}\n"; + ofs.close(); +} +#endif // WASM_OUTPUT_REPORT_HPP \ No newline at end of file diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index 9814b5eb5..ba8194c70 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -116,12 +116,70 @@ class Profile_t { } } + void write_as_json(std::ostream &os) const { + os << " \"profile_summary\": {\n"; + if (PROFILE_STEP) { + os << " \"total_push_operations\": " + << op_count[static_cast(StepProfileKind::PUSH)] << ",\n"; + os << " \"total_pop_operations\": " + << op_count[static_cast(StepProfileKind::POP)] << ",\n"; + os << " \"total_peek_operations\": " + << op_count[static_cast(StepProfileKind::PEEK)] << ",\n"; + os << " \"total_shift_operations\": " + << op_count[static_cast(StepProfileKind::SHIFT)] << ",\n"; + os << " \"total_set_operations\": " + << op_count[static_cast(StepProfileKind::SET)] << ",\n"; + os << " \"total_get_operations\": " + << op_count[static_cast(StepProfileKind::GET)] << ",\n"; + os << " \"total_binary_operations\": " + << op_count[static_cast(StepProfileKind::BINARY)] + << ",\n"; + os << " \"total_tree_fill_operations\": " + << op_count[static_cast(StepProfileKind::TREE_FILL)] + << ",\n"; + os << " \"total_cursor_move_operations\": " + << op_count[static_cast(StepProfileKind::CURSOR_MOVE)] + << ",\n"; + os << " \"total_other_instructions_executed\": " << step_count + << ",\n"; + os << " \"total_mem_grow_operations\": " + << op_count[static_cast(StepProfileKind::MEM_GROW)] + << ",\n"; + os << " \"total_snapshot_create_operations\": " + << op_count[static_cast(StepProfileKind::SNAPSHOT_CREATE)] + << ",\n"; + os << " \"total_sym_eval_operations\": " + << op_count[static_cast(StepProfileKind::SYM_EVAL)] + << "\n"; + } + if (PROFILE_TIME) { + os << " \"total_time_instruction_execution_s\": " + << std::setprecision(15) + << time_count[static_cast(TimeProfileKind::INSTR)] + << ",\n"; + os << " \"total_time_solver_s\": " + << std::setprecision(15) + << time_count[static_cast(TimeProfileKind::SOLVER)] + << ",\n"; + os << " \"total_time_resuming_from_snapshot_s\": " + << std::setprecision(15) + << time_count[static_cast( + TimeProfileKind::RESUME_SNAPSHOT)] + << ",\n"; + os << " \"total_time_counting_symbolic_size_s\": " + << std::setprecision(15) + << time_count[static_cast( + TimeProfileKind::COUNT_SYM_SIZE)] + << "\n"; + } + os << " }\n"; + } + // record the time spent in main instruction execution, in seconds void add_instruction_time(TimeProfileKind kind, double time) { time_count[static_cast(kind)] += time; } -private: int step_count; std::array(StepProfileKind::OperationCount)> op_count; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 2bcfe7aca..cc1e8652e 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -14,6 +14,7 @@ #include #include #include +#include #include #include #include @@ -884,6 +885,24 @@ inline int Snapshot_t::cost_of_snapshot() { return 5.336 * (cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy); } + +struct OverallResult { + int unexplored_count = 0; + int finished_count = 0; + int failed_count = 0; + int not_to_explore_count = 0; + int unreachable_count = 0; + + void print() { + std::cout << "Explore Tree Overall Result:" << std::endl; + std::cout << " Unexplored paths: " << unexplored_count << std::endl; + std::cout << " Finished paths: " << finished_count << std::endl; + std::cout << " Failed paths: " << failed_count << std::endl; + std::cout << " Unreachable paths: " << unreachable_count << std::endl; + std::cout << " NotToExplore paths: " << not_to_explore_count << std::endl; + } +}; + class ExploreTree_t { public: explicit ExploreTree_t() @@ -1009,6 +1028,16 @@ class ExploreTree_t { } std::monostate dump_graphviz(std::string filepath) { + std::filesystem::path out_path(filepath); + auto parent = out_path.parent_path(); + if (!parent.empty()) { + std::error_code ec; + std::filesystem::create_directories(parent, ec); + if (ec) { + throw std::runtime_error("Failed to create output directory: " + + ec.message()); + } + } std::ofstream ofs(filepath); if (!ofs.is_open()) { throw std::runtime_error("Failed to open " + filepath + " for writing"); @@ -1017,45 +1046,35 @@ class ExploreTree_t { return std::monostate(); } - std::monostate print_overall_result() { - // Print how many paths have been explored, how many paths are unreachable, - // how many paths are failed, how many paths are finished successfully - int unexplored_count = 0; - int finished_count = 0; - int failed_count = 0; - int not_to_explore_count = 0; - int unreachable_count = 0; + OverallResult read_current_overall_result() { + OverallResult result; std::function dfs = [&](NodeBox *node) { if (auto if_else_node = dynamic_cast(node->node.get())) { dfs(if_else_node->true_branch.get()); dfs(if_else_node->false_branch.get()); } else if (dynamic_cast(node->node.get())) { - unexplored_count += 1; + result.unexplored_count += 1; } else if (dynamic_cast(node->node.get())) { - finished_count += 1; + result.finished_count += 1; } else if (dynamic_cast(node->node.get())) { - failed_count += 1; + result.failed_count += 1; } else if (dynamic_cast(node->node.get())) { - unreachable_count += 1; + result.unreachable_count += 1; } else if (dynamic_cast(node->node.get())) { // Snapshot node is considered unexplored - unexplored_count += 1; + result.unexplored_count += 1; } else if (dynamic_cast(node->node.get())) { - not_to_explore_count += 1; + result.not_to_explore_count += 1; } else { throw std::runtime_error("Unknown node type in explore tree"); } }; dfs(root.get()); - std::cout << "Explore Tree Overall Result:" << std::endl; - std::cout << " Unexplored paths: " << unexplored_count << std::endl; - std::cout << " Finished paths: " << finished_count << std::endl; - std::cout << " Failed paths: " << failed_count << std::endl; - std::cout << " Unreachable paths: " << unreachable_count << std::endl; - std::cout << " NotToExplore paths: " << not_to_explore_count << std::endl; - return std::monostate(); + return result; } + std::monostate print_overall_result() {} + NodeBox *pick_unexplored() { // Pick an unexplored node from the tree // For now, we just iterate through the tree and return the first unexplored From 1818f538d45c0f2ff4f5158514ecabc61d0a83e1 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 3 Nov 2025 16:05:28 -0500 Subject: [PATCH 075/105] a script for running and cleaning up benchmark executables. --- benchmarks/pldi2026/btree/run.py | 74 ++++++++++++++++++++++++++++++++ 1 file changed, 74 insertions(+) create mode 100644 benchmarks/pldi2026/btree/run.py diff --git a/benchmarks/pldi2026/btree/run.py b/benchmarks/pldi2026/btree/run.py new file mode 100644 index 000000000..4cb40e1ec --- /dev/null +++ b/benchmarks/pldi2026/btree/run.py @@ -0,0 +1,74 @@ +import os +import shutil +import sys +import subprocess +from pathlib import Path +import argparse + + +HERE = Path(__file__).resolve().parent +ME = Path(__file__).name + + +def is_executable(path: Path) -> bool: + if not path.is_file(): + return False + # executable bit or .exe suffix + return os.access(str(path), os.X_OK) or path.suffix.lower() == ".exe" + + +def run_all(targets: list[Path], action): + for file_path in targets: + if not is_executable(file_path): + continue + file_name = file_path.name.removesuffix(".exe") + output_path = f"{file_name}.output" + if action == "run": + env = os.environ.copy() + env.update({"OUTPUT_DIR": output_path}) + + print("Now executing: " + str(file_path)) + proc = subprocess.Popen( + [str(file_path.resolve())], stderr=subprocess.STDOUT, env=env + ) + rc = proc.wait() + + if rc != 0: + print(f"{file_name} exited with return code {rc}", file=sys.stderr) + elif action == "clean": + p = Path(output_path) + if p.exists(): + try: + if p.is_dir(): + shutil.rmtree(p) + except Exception as e: + print(f"Failed to remove {output_path}: {e}", file=sys.stderr) + +def main(): + parser = argparse.ArgumentParser() + parser.add_argument( + "-r", + "--run-all", + action="store_true", + help="Run all compiled executables in the current directory", + ) + parser.add_argument( + "--clean", + action="store_true" + ) + args = parser.parse_args() + + if not args.run_all and not args.clean: + parser.print_help() + return 0 + + targets = list(sorted(list(Path(".").iterdir()))) + if args.run_all: + run_all(targets, action="run") + elif args.clean: + run_all(targets, action="clean") + + + +if __name__ == "__main__": + sys.exit(main()) From 6dd52b2a553306ea2ede2a8e14d1469fd465f3a2 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 3 Nov 2025 20:05:32 -0500 Subject: [PATCH 076/105] never build an expression twice --- benchmarks/pldi2026/btree/compile.py | 2 +- benchmarks/pldi2026/btree/run.py | 2 ++ headers/wasm/smt_solver.hpp | 28 +++++++++++++++++++++------- headers/wasm/symbolic_rt.hpp | 14 +++++++++++++- 4 files changed, 37 insertions(+), 9 deletions(-) diff --git a/benchmarks/pldi2026/btree/compile.py b/benchmarks/pldi2026/btree/compile.py index 8c0b53722..5e1555b31 100644 --- a/benchmarks/pldi2026/btree/compile.py +++ b/benchmarks/pldi2026/btree/compile.py @@ -17,7 +17,7 @@ DEFAULT_FLAGS = [ "-std=c++17", "-g", - "-O0", + "-O3", "-Wall", "-Wextra", "-DUSE_IMM", diff --git a/benchmarks/pldi2026/btree/run.py b/benchmarks/pldi2026/btree/run.py index 4cb40e1ec..b462af292 100644 --- a/benchmarks/pldi2026/btree/run.py +++ b/benchmarks/pldi2026/btree/run.py @@ -23,6 +23,8 @@ def run_all(targets: list[Path], action): continue file_name = file_path.name.removesuffix(".exe") output_path = f"{file_name}.output" + if Path(output_path).exists(): + continue if action == "run": env = os.environ.copy() env.update({"OUTPUT_DIR": output_path}) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 5df683f76..122f18aab 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -7,6 +7,7 @@ #include "wasm/profile.hpp" #include "z3++.h" #include +#include #include #include #include @@ -15,15 +16,16 @@ class Solver { public: Solver() {} - std::optional solve(const std::vector &conditions) { + std::optional solve(std::vector &conditions) { z3::solver z3_solver(z3_ctx); z3::check_result solver_result; { + auto timer = ManagedTimer(TimeProfileKind::SOLVER); // make an conjunction of all conditions auto conjunction = to_z3_conjunction(conditions); // call z3 to solve the condition - auto timer = ManagedTimer(TimeProfileKind::SOLVER); - z3_solver.add(conjunction); // NOTE: half of the solver time is spent in solver.add + // NOTE: half of the solver time is spent in solver.add + z3_solver.add(conjunction); solver_result = z3_solver.check(); } switch (solver_result) { @@ -56,9 +58,9 @@ class Solver { } private: - z3::expr to_z3_conjunction(const std::vector &conditions) { + z3::expr to_z3_conjunction(std::vector &conditions) { z3::expr conjunction = z3_ctx.bool_val(true); - for (const auto &cond : conditions) { + for (auto &cond : conditions) { auto z3_cond = build_z3_expr(cond); conjunction = conjunction && z3_cond != z3_ctx.bv_val(0, 32); } @@ -70,10 +72,13 @@ class Solver { } z3::context z3_ctx; - z3::expr build_z3_expr(const SymVal &sym_val); + z3::expr build_z3_expr(SymVal &sym_val); + +private: + z3::expr build_z3_expr_aux(SymVal &sym_val); }; -inline z3::expr Solver::build_z3_expr(const SymVal &sym_val) { +inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { if (auto sym = std::dynamic_pointer_cast(sym_val.symptr)) { return z3_ctx.bv_const(("s_" + std::to_string(sym->get_id())).c_str(), 32); } else if (auto concrete = @@ -150,4 +155,13 @@ inline z3::expr Solver::build_z3_expr(const SymVal &sym_val) { } throw std::runtime_error("Unsupported symbolic value type"); } + +inline z3::expr Solver::build_z3_expr(SymVal &sym_val) { + if (sym_val.z3_expr) { + return *sym_val.z3_expr; + } + auto e = build_z3_expr_aux(sym_val); + sym_val.z3_expr = std::make_shared(e); + return e; +} #endif // SMT_SOLVER_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index cc1e8652e..998af1e94 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -10,6 +10,7 @@ #include "immer/vector_transient.hpp" #include "profile.hpp" #include "utils.hpp" +#include "z3++.h" #include #include #include @@ -90,6 +91,7 @@ static std::shared_ptr ZeroByte = struct SymVal { std::shared_ptr symptr; + std::shared_ptr z3_expr; SymVal() : symptr(ZERO) {} SymVal(std::shared_ptr symptr) : symptr(symptr) {} @@ -226,11 +228,21 @@ inline SymVal SymVal::make_binary(Operation op, const SymVal &lhs, assert(lhs.symptr != nullptr && rhs.symptr != nullptr); return SymVal(SymBookKeeper.allocate(op, lhs, rhs)); } +static std::unordered_map SymbolCache; + inline SymVal SymVal::makeSymbolic() const { auto concrete = dynamic_cast(symptr.get()); if (concrete) { // If the symbolic value is a concrete value, use it to create a symbol - return SymVal(SymBookKeeper.allocate(concrete->value.toInt())); + auto id = concrete->value.toInt(); + auto it = SymbolCache.find(id); + if (it != SymbolCache.end()) { + return it->second; + } + auto sym = Symbol(id); + auto ptr = SymBookKeeper.allocate(sym); + return SymVal(ptr); + } else { throw std::runtime_error( "Cannot make symbolic a non-concrete symbolic value"); From 7cdfe5393921462c697751bc17a487eae25c54eb Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 5 Nov 2025 15:57:48 -0500 Subject: [PATCH 077/105] update sym_assert and timer --- headers/wasm/concolic_driver.hpp | 1 - headers/wasm/profile.hpp | 41 +++++++++++++++---- headers/wasm/smt_solver.hpp | 17 +++++++- headers/wasm/symbolic_rt.hpp | 4 ++ .../scala/wasm/StagedConcolicMiniWasm.scala | 12 +++++- 5 files changed, 64 insertions(+), 11 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index e13e58824..7211a5a25 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -31,7 +31,6 @@ class ConcolicDriver { private: void main_exploration_loop(); - Solver solver; std::function entrypoint; std::optional tree_file; std::vector work_list; diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index ba8194c70..c32e2b518 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -7,6 +7,7 @@ #include #include #include +#include enum class StepProfileKind { PUSH, @@ -157,8 +158,7 @@ class Profile_t { << std::setprecision(15) << time_count[static_cast(TimeProfileKind::INSTR)] << ",\n"; - os << " \"total_time_solver_s\": " - << std::setprecision(15) + os << " \"total_time_solver_s\": " << std::setprecision(15) << time_count[static_cast(TimeProfileKind::SOLVER)] << ",\n"; os << " \"total_time_resuming_from_snapshot_s\": " @@ -191,23 +191,50 @@ class Profile_t { static Profile_t Profile; -class ManagedTimer { +class Timer { public: - ManagedTimer() = delete; - ManagedTimer(TimeProfileKind kind) : kind(kind) { + Timer() = delete; + Timer(TimeProfileKind kind) : kind(kind) { + elapsed = std::chrono::duration::zero(); start = std::chrono::high_resolution_clock::now(); } - ~ManagedTimer() { + ~Timer() { auto end = std::chrono::high_resolution_clock::now(); - std::chrono::duration elapsed = end - start; + elapsed += end - start; Profile.add_instruction_time(kind, elapsed.count()); } + void stop() { elapsed += std::chrono::high_resolution_clock::now() - start; } + void resume() { start = std::chrono::high_resolution_clock::now(); } private: + std::chrono::duration elapsed; TimeProfileKind kind; std::chrono::high_resolution_clock::time_point start; }; +static std::vector TimerStack = []() { + std::vector v; + v.reserve(3); // initial capacity + return v; +}(); + +class ManagedTimer { +public: + ManagedTimer() = delete; + ManagedTimer(TimeProfileKind kind) { + if (TimerStack.size() > 0) { + TimerStack.back().stop(); + } + TimerStack.emplace_back(kind); + } + ~ManagedTimer() { + TimerStack.pop_back(); + if (TimerStack.size() > 0) { + TimerStack.back().resume(); + } + } +}; + struct CostManager_t { int instr_cost; diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 122f18aab..09c91e89f 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -11,6 +11,7 @@ #include #include #include +#include #include class Solver { @@ -73,11 +74,11 @@ class Solver { z3::context z3_ctx; z3::expr build_z3_expr(SymVal &sym_val); - -private: z3::expr build_z3_expr_aux(SymVal &sym_val); }; +static Solver solver; + inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { if (auto sym = std::dynamic_pointer_cast(sym_val.symptr)) { return z3_ctx.bv_const(("s_" + std::to_string(sym->get_id())).c_str(), 32); @@ -164,4 +165,16 @@ inline z3::expr Solver::build_z3_expr(SymVal &sym_val) { sym_val.z3_expr = std::make_shared(e); return e; } + +inline std::monostate GENSYM_SYM_ASSERT(SymVal &sym_cond) { + std::vector conds = ExploreTree.collect_current_path_conds(); + conds.push_back(sym_cond.negate()); + auto result = solver.solve(conds); + if (result.has_value()) { + std::cout << "Symbolic assertion failed" << std::endl; + throw std::runtime_error("Symbolic assertion failed"); + } + return std::monostate{}; +} + #endif // SMT_SOLVER_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 998af1e94..fe268ed50 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -957,6 +957,10 @@ class ExploreTree_t { return cursor->fillNotToExploreNode(); } + std::vector collect_current_path_conds() { + return cursor->collect_path_conds(); + } + bool worth_to_create_snapshot() { if (!ENABLE_COST_MODEL) { return REUSE_SNAPSHOT; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 308ce55a4..aebf11ac8 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -576,7 +576,11 @@ trait StagedWasmEvaluator extends SAIOps { } () case Import("i32", "sym_assert", _) => - // TODO: implement sym_assert + val (condTy, newCtx) = ctx.pop() + val v = Stack.popC(condTy) + val s = Stack.popS(condTy) + runtimeSymAssert(s) + runtimeAssert(v.toInt != 0) eval(rest, kont, mkont, trail)(ctx.pop()._2) case Import(m, f, _) => throw new Exception(s"Unknown import $m.$f at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") @@ -715,6 +719,10 @@ trait StagedWasmEvaluator extends SAIOps { "assert-true".reflectCtrlWith[Unit](b) } + def runtimeSymAssert(s: StagedSymbolicNum): Rep[Unit] = { + "sym-assert-true".reflectCtrlWith[Unit](s.s) + } + // stack operations object Stack { def shiftC(offset: Int, size: Int) = { @@ -1578,6 +1586,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("SymEnv.read("); shallow(sym); emit(")") case Node(_, "assert-true", List(cond), _) => emit("GENSYM_ASSERT("); shallow(cond); emit(")") + case Node(_, "sym-assert-true", List(s_cond), _) => + emit("GENSYM_SYM_ASSERT("); shallow(s_cond); emit(")") case Node(_, "tree-fill-if-else", List(sym, id), _) => emit("ExploreTree.fillIfElseNode("); shallow(sym); emit(", "); emit(id.toString); emit(")") case Node(_, "tree-fill-not-to-explore", List(), _) => From efb8144ae1bc83a0f37815b1d18aebb46498e15f Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 6 Nov 2025 11:42:51 -0500 Subject: [PATCH 078/105] refactor operator to explicit methods --- headers/wasm/concrete_rt.hpp | 124 +++++++++++++++--- headers/wasm/symbolic_rt.hpp | 68 ++++++++-- .../scala/wasm/StagedConcolicMiniWasm.scala | 75 +++++------ 3 files changed, 201 insertions(+), 66 deletions(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index ea321f456..a63d2d7e0 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -17,30 +17,121 @@ struct Num { Num(int64_t value) : value(value) {} Num() : value(0) {} int64_t value; + int32_t toInt() const { return static_cast(value); } + uint32_t toUInt() const { return static_cast(value); } + // Helper to create a Wasm Boolean result (1 or 0 as Num) + Num WasmBool(bool condition) const { return Num(condition ? 1 : 0); } // TODO: support different bit width operations, for now we just assume all // oprands are i32 - bool operator==(const Num &other) const { return toInt() == other.toInt(); } - bool operator!=(const Num &other) const { return !(*this == other); } - Num operator+(const Num &other) const { return Num(toInt() + other.toInt()); } - Num operator-(const Num &other) const { return Num(toInt() - other.toInt()); } - Num operator*(const Num &other) const { return Num(toInt() * other.toInt()); } - Num operator/(const Num &other) const { - if (other.toInt() == 0) { - throw std::runtime_error("Division by zero"); + // i32.eq (Equals): *this == other + inline Num i32_eq(const Num &other) const { + return WasmBool(this->toUInt() == other.toUInt()); + } + + // i32.ne (Not Equals): *this != other + inline Num i32_ne(const Num &other) const { + return WasmBool(this->toUInt() != other.toUInt()); + } + + // i32.lt_s (Signed Less Than): *this < other + inline Num i32_lt_s(const Num &other) const { + return WasmBool(this->toInt() < other.toInt()); + } + + // i32.lt_u (Unsigned Less Than): *this < other (unsigned) + inline Num i32_lt_u(const Num &other) const { + return WasmBool(this->toUInt() < other.toUInt()); + } + + // i32.le_s (Signed Less Than or Equal): *this <= other + inline Num i32_le_s(const Num &other) const { + return WasmBool(this->toInt() <= other.toInt()); + } + // i32.le_u (Unsigned Less Than or Equal): *this <= other (unsigned) + inline Num i32_le_u(const Num &other) const { + return WasmBool(this->toUInt() <= other.toUInt()); + } + + // i32.gt_s (Signed Greater Than): *this > other + inline Num i32_gt_s(const Num &other) const { + return WasmBool(this->toInt() > other.toInt()); + } + + // i32.gt_u (Unsigned Greater Than): *this > other (unsigned) + inline Num i32_gt_u(const Num &other) const { + return WasmBool(this->toUInt() > other.toUInt()); + } + + // i32.ge_s (Signed Greater Than or Equal): *this >= other + inline Num i32_ge_s(const Num &other) const { + return WasmBool(this->toInt() >= other.toInt()); + } + + // i32.ge_u (Unsigned Greater Than or Equal): *this >= other (unsigned) + inline Num i32_ge_u(const Num &other) const { + return WasmBool(this->toUInt() >= other.toUInt()); + } + + // i32.add (Wrapping addition) + inline Num i32_add(const Num &other) const { + uint32_t result_u = this->toUInt() + other.toUInt(); + return Num(static_cast(result_u)); + } + + // i32.sub (Wrapping subtraction) + inline Num i32_sub(const Num &other) const { + uint32_t result_u = this->toUInt() - other.toUInt(); + return Num(static_cast(result_u)); + } + + // i32.mul (Wrapping multiplication) + inline Num i32_mul(const Num &other) const { + uint32_t result_u = this->toUInt() * other.toUInt(); + return Num(static_cast(result_u)); + } + + // i32.div_s (Signed division with traps) + inline Num i32_div_s(const Num &other) const { + int32_t divisor = other.toInt(); + int32_t dividend = this->toInt(); + + if (divisor == 0) { + throw std::runtime_error("i32.div_s: Division by zero"); } - return Num(toInt() / other.toInt()); + + return Num(dividend / divisor); + } + + // i32.shl (Shift Left): *this << other (shift count masked by 31) + inline Num i32_shl(const Num &other) const { + uint32_t shift_amount = other.toUInt() & 0x1F; + uint32_t result_u = toUInt() << shift_amount; + return Num(static_cast(result_u)); + } + + // i32.shr_s (Signed Shift Right): *this >> other (Arithmetic shift) + inline Num i32_shr_s(const Num &other) const { + // Wasm masks the shift amount by 31 (0x1F) + uint32_t shift_amount = other.toUInt() & 0x1F; + int32_t result_s = toInt() >> shift_amount; + return Num(result_s); } - Num operator<(const Num &other) const { return Num(toInt() < other.toInt()); } - Num operator<=(const Num &other) const { - return Num(toInt() <= other.toInt()); + + // i32.shr_u (Unsigned Shift Right): *this >>> other (Logical shift) + inline Num i32_shr_u(const Num &other) const { + // Wasm masks the shift amount by 31 (0x1F) + uint32_t shift_amount = other.toUInt() & 0x1F; + uint32_t result_u = toUInt() >> shift_amount; + return Num(static_cast(result_u)); } - Num operator>(const Num &other) const { return Num(toInt() > other.toInt()); } - Num operator>=(const Num &other) const { - return Num(toInt() >= other.toInt()); + + // i32.and (Bitwise AND) + inline Num i32_and(const Num &other) const { + uint32_t result_u = this->toUInt() & other.toUInt(); + return Num(static_cast(result_u)); } - Num operator&(const Num &other) const { return Num(toInt() & other.toInt()); } }; static Num I32V(int v) { return v; } @@ -303,6 +394,7 @@ struct Memory_t { } }; + static Memory_t Memory(1); // 1 page memory #endif // WASM_CONCRETE_RT_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index fe268ed50..43e991313 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -1251,29 +1251,75 @@ static EvalRes eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { auto rhs_res = eval_sym_expr(operation->rhs, sym_env); auto lhs = lhs_res.value; auto rhs = rhs_res.value; + auto lhs_width = lhs_res.width; + auto rhs_width = rhs_res.width; switch (operation->op) { case ADD: - return EvalRes(lhs + rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_add(rhs), 32); + } else { + assert(false && "TODO"); + } case SUB: - return EvalRes(lhs - rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_sub(rhs), 32); + } else { + assert(false && "TODO"); + } case MUL: - return EvalRes(lhs * rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_mul(rhs), 32); + } else { + assert(false && "TODO"); + } case DIV: - return EvalRes(lhs / rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_div_s(rhs), 32); + } else { + assert(false && "TODO"); + } case LT: - return EvalRes(lhs < rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_lt_s(rhs), 32); + } else { + assert(false && "TODO"); + } case LEQ: - return EvalRes(lhs <= rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_le_s(rhs), 32); + } else { + assert(false && "TODO"); + } case GT: - return EvalRes(lhs > rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_gt_s(rhs), 32); + } else { + assert(false && "TODO"); + } case GEQ: - return EvalRes(lhs >= rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_ge_s(rhs), 32); + } else { + assert(false && "TODO"); + } case NEQ: - return EvalRes(lhs != rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_ne(rhs), 32); + } else { + assert(false && "TODO"); + } case EQ: - return EvalRes(lhs == rhs, 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_eq(rhs), 32); + } else { + assert(false && "TODO"); + } case B_AND: - return EvalRes(Num(I64V(lhs.value & rhs.value)), 32); + if (lhs_width == 32 && rhs_width == 32) { + return EvalRes(lhs.i32_and(rhs), 32); + } else { + assert(false && "TODO"); + } case CONCAT: { auto lhs_width = lhs_res.width; auto rhs_width = rhs_res.width; diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index aebf11ac8..48d902801 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -581,7 +581,7 @@ trait StagedWasmEvaluator extends SAIOps { val s = Stack.popS(condTy) runtimeSymAssert(s) runtimeAssert(v.toInt != 0) - eval(rest, kont, mkont, trail)(ctx.pop()._2) + eval(rest, kont, mkont, trail)(newCtx) case Import(m, f, _) => throw new Exception(s"Unknown import $m.$f at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } @@ -667,8 +667,6 @@ trait StagedWasmEvaluator extends SAIOps { def evalTop(mkont: Rep[MCont[Unit]], main: Option[String]): Rep[Unit] = { Counter.reset() - Predef.println("[DEBUG]" + module) - Predef.println("[DEBUG] module.defs: " + module.defs) val funBody: FuncBodyDef = main match { case Some(func_name) => module.defs.flatMap({ @@ -1096,9 +1094,9 @@ trait StagedWasmEvaluator extends SAIOps { def <(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) } } @@ -1132,9 +1130,9 @@ trait StagedWasmEvaluator extends SAIOps { def <=(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-le".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-les".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-le".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-les".reflectCtrlWith[Num](num.i, rhs.i)) } } @@ -1150,9 +1148,9 @@ trait StagedWasmEvaluator extends SAIOps { def >=(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) } } @@ -1303,9 +1301,9 @@ trait StagedWasmEvaluator extends SAIOps { def <(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-lts".reflectCtrlWith[SymVal](num.s, rhs.s)) case (NumType(I64Type), NumType(I64Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-lts".reflectCtrlWith[SymVal](num.s, rhs.s)) } } @@ -1339,9 +1337,9 @@ trait StagedWasmEvaluator extends SAIOps { def <=(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-les".reflectCtrlWith[SymVal](num.s, rhs.s)) case (NumType(I64Type), NumType(I64Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-les".reflectCtrlWith[SymVal](num.s, rhs.s)) } } @@ -1357,9 +1355,9 @@ trait StagedWasmEvaluator extends SAIOps { def >=(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-ges".reflectCtrlWith[SymVal](num.s, rhs.s)) case (NumType(I64Type), NumType(I64Type)) => - StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) + StagedSymbolicNum(NumType(I32Type), "sym-relation-ges".reflectCtrlWith[SymVal](num.s, rhs.s)) } } @@ -1516,40 +1514,39 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "sym-is-zero", List(s_num), _) => shallow(s_num); emit(".is_zero()") case Node(_, "binary-add", List(lhs, rhs), _) => - shallow(lhs); emit(" + "); shallow(rhs) + shallow(lhs); emit(".i32_add("); shallow(rhs); emit(")") case Node(_, "binary-sub", List(lhs, rhs), _) => - // todo: avoid using c++ operator, use explicit method call so operator's precedence issues won't exist - emit("("); shallow(lhs); emit(" - "); shallow(rhs); emit(")") + shallow(lhs); emit(".i32_sub("); shallow(rhs); emit(")") case Node(_, "binary-mul", List(lhs, rhs), _) => - shallow(lhs); emit(" * "); shallow(rhs) + shallow(lhs); emit(".i32_mul("); shallow(rhs); emit(")") case Node(_, "binary-div", List(lhs, rhs), _) => - shallow(lhs); emit(" / "); shallow(rhs) + shallow(lhs); emit(".i32_div_s("); shallow(rhs); emit(")") case Node(_, "binary-shl", List(lhs, rhs), _) => - shallow(lhs); emit(" << "); shallow(rhs) + shallow(lhs); emit(".i32_shl("); shallow(rhs); emit(")") case Node(_, "binary-shr", List(lhs, rhs), _) => - shallow(lhs); emit(" >> "); shallow(rhs) + shallow(lhs); emit(".i32_shr("); shallow(rhs); emit(")") case Node(_, "binary-and", List(lhs, rhs), _) => - shallow(lhs); emit(" & "); shallow(rhs) + shallow(lhs); emit(".i32_and("); shallow(rhs); emit(")") case Node(_, "relation-eq", List(lhs, rhs), _) => - shallow(lhs); emit(" == "); shallow(rhs) + shallow(lhs); emit(".i32_eq("); shallow(rhs); emit(")") case Node(_, "relation-ne", List(lhs, rhs), _) => - shallow(lhs); emit(" != "); shallow(rhs) - case Node(_, "relation-lt", List(lhs, rhs), _) => - shallow(lhs); emit(" < "); shallow(rhs) + shallow(lhs); emit(".i32_ne("); shallow(rhs); emit(")") + case Node(_, "relation-lts", List(lhs, rhs), _) => + shallow(lhs); emit(".i32_lt_s("); shallow(rhs); emit(")") case Node(_, "relation-ltu", List(lhs, rhs), _) => - shallow(lhs); emit(" < "); shallow(rhs) + shallow(lhs); emit(".i32_lt_u("); shallow(rhs); emit(")") case Node(_, "relation-gt", List(lhs, rhs), _) => - shallow(lhs); emit(" > "); shallow(rhs) + shallow(lhs); emit(".i32_gt_s("); shallow(rhs); emit(")") case Node(_, "relation-gtu", List(lhs, rhs), _) => - shallow(lhs); emit(" > "); shallow(rhs) - case Node(_, "relation-le", List(lhs, rhs), _) => - shallow(lhs); emit(" <= "); shallow(rhs) + shallow(lhs); emit(".i32_gt_u("); shallow(rhs); emit(")") + case Node(_, "relation-les", List(lhs, rhs), _) => + shallow(lhs); emit(".i32_le_s("); shallow(rhs); emit(")") case Node(_, "relation-leu", List(lhs, rhs), _) => - shallow(lhs); emit(" <= "); shallow(rhs) - case Node(_, "relation-ge", List(lhs, rhs), _) => - shallow(lhs); emit(" >= "); shallow(rhs) + shallow(lhs); emit(".i32_le_u("); shallow(rhs); emit(")") + case Node(_, "relation-ges", List(lhs, rhs), _) => + shallow(lhs); emit(".i32_ge_s("); shallow(rhs); emit(")") case Node(_, "relation-geu", List(lhs, rhs), _) => - shallow(lhs); emit(" >= "); shallow(rhs) + shallow(lhs); emit(".i32_ge_u("); shallow(rhs); emit(")") case Node(_, "sym-binary-add", List(lhs, rhs), _) => shallow(lhs); emit(".add("); shallow(rhs); emit(")") case Node(_, "sym-binary-sub", List(lhs, rhs), _) => @@ -1560,13 +1557,13 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".div("); shallow(rhs); emit(")") case Node(_, "sym-binary-and", List(lhs, rhs), _) => shallow(lhs); emit(".bitwise_and("); shallow(rhs); emit(")") - case Node(_, "sym-relation-le", List(lhs, rhs), _) => + case Node(_, "sym-relation-les", List(lhs, rhs), _) => shallow(lhs); emit(".le("); shallow(rhs); emit(")") case Node(_, "sym-relation-leu", List(lhs, rhs), _) => shallow(lhs); emit(".leu("); shallow(rhs); emit(")") - case Node(_, "sym-relation-lt", List(lhs, rhs), _) => + case Node(_, "sym-relation-lts", List(lhs, rhs), _) => shallow(lhs); emit(".lt("); shallow(rhs); emit(")") - case Node(_, "sym-relation-ge", List(lhs, rhs), _) => + case Node(_, "sym-relation-ges", List(lhs, rhs), _) => shallow(lhs); emit(".ge("); shallow(rhs); emit(")") case Node(_, "sym-relation-geu", List(lhs, rhs), _) => shallow(lhs); emit(".geu("); shallow(rhs); emit(")") From 0552131a7929ba2e1b0875c10c2f1d555680f81f Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 6 Nov 2025 22:40:13 -0500 Subject: [PATCH 079/105] fixed a bug, zero initialize local variables --- headers/wasm/concolic_driver.hpp | 17 +++++- headers/wasm/concrete_rt.hpp | 92 +++++++++++++++++++++++++------- headers/wasm/symbolic_rt.hpp | 5 ++ 3 files changed, 93 insertions(+), 21 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 7211a5a25..e9da77c1d 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -3,11 +3,11 @@ #include "concrete_rt.hpp" #include "config.hpp" +#include "output_report.hpp" #include "profile.hpp" #include "smt_solver.hpp" #include "symbolic_rt.hpp" #include "utils.hpp" -#include "output_report.hpp" #include #include #include @@ -103,13 +103,26 @@ inline void ConcolicDriver::main_exploration_loop() { try { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); - { node->reach_here(entrypoint); } + if (REUSE_SNAPSHOT) { + node->reach_here(entrypoint); + } else { + auto timer = ManagedTimer(TimeProfileKind::INSTR); + ExploreTree.reset_cursor(); + reset_stacks(); + entrypoint(); + } GENSYM_INFO("Execution finished successfully with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); } catch (std::runtime_error &e) { std::cout << "Caught runtime error: " << e.what() << std::endl; ExploreTree.fillFailedNode(); + + if (std::string(e.what()) == "Symbolic assertion failed") { + GENSYM_INFO("Symbolic assertion failed, continuing to next path..."); + continue; + } + GENSYM_INFO("Caught runtime error with symbolic environment:"); GENSYM_INFO(SymEnv.to_string()); switch (EXPLORE_MODE) { diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index a63d2d7e0..4a2d4ad58 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -21,75 +21,115 @@ struct Num { int32_t toInt() const { return static_cast(value); } uint32_t toUInt() const { return static_cast(value); } + // debug printer: enabled only when -DDEBUG + static inline void debug_print(const char *op, const Num &a, const Num &b, + const Num &res) { +#ifdef DEBUG_OP + std::cout << "[Debug] " << op << ": lhs=" << static_cast(a.value) + << " rhs=" << static_cast(b.value) + << " -> res=" << static_cast(res.value) << std::endl; +#endif + } + // Helper to create a Wasm Boolean result (1 or 0 as Num) - Num WasmBool(bool condition) const { return Num(condition ? 1 : 0); } + Num WasmBool(bool condition) const { + Num res(condition ? 1 : 0); + debug_print("WasmBool", *this, *this, res); + return res; + } // TODO: support different bit width operations, for now we just assume all // oprands are i32 // i32.eq (Equals): *this == other inline Num i32_eq(const Num &other) const { - return WasmBool(this->toUInt() == other.toUInt()); + Num res = WasmBool(this->toUInt() == other.toUInt()); + debug_print("i32.eq", *this, other, res); + return res; } // i32.ne (Not Equals): *this != other inline Num i32_ne(const Num &other) const { - return WasmBool(this->toUInt() != other.toUInt()); + Num res = WasmBool(this->toUInt() != other.toUInt()); + debug_print("i32.ne", *this, other, res); + return res; } // i32.lt_s (Signed Less Than): *this < other inline Num i32_lt_s(const Num &other) const { - return WasmBool(this->toInt() < other.toInt()); + Num res = WasmBool(this->toInt() < other.toInt()); + debug_print("i32.lt_s", *this, other, res); + return res; } // i32.lt_u (Unsigned Less Than): *this < other (unsigned) inline Num i32_lt_u(const Num &other) const { - return WasmBool(this->toUInt() < other.toUInt()); + Num res = WasmBool(this->toUInt() < other.toUInt()); + debug_print("i32.lt_u", *this, other, res); + return res; } // i32.le_s (Signed Less Than or Equal): *this <= other inline Num i32_le_s(const Num &other) const { - return WasmBool(this->toInt() <= other.toInt()); + Num res = WasmBool(this->toInt() <= other.toInt()); + debug_print("i32.le_s", *this, other, res); + return res; } // i32.le_u (Unsigned Less Than or Equal): *this <= other (unsigned) inline Num i32_le_u(const Num &other) const { - return WasmBool(this->toUInt() <= other.toUInt()); + Num res = WasmBool(this->toUInt() <= other.toUInt()); + debug_print("i32.le_u", *this, other, res); + return res; } // i32.gt_s (Signed Greater Than): *this > other inline Num i32_gt_s(const Num &other) const { - return WasmBool(this->toInt() > other.toInt()); + Num res = WasmBool(this->toInt() > other.toInt()); + debug_print("i32.gt_s", *this, other, res); + return res; } // i32.gt_u (Unsigned Greater Than): *this > other (unsigned) inline Num i32_gt_u(const Num &other) const { - return WasmBool(this->toUInt() > other.toUInt()); + Num res = WasmBool(this->toUInt() > other.toUInt()); + debug_print("i32.gt_u", *this, other, res); + return res; } // i32.ge_s (Signed Greater Than or Equal): *this >= other inline Num i32_ge_s(const Num &other) const { - return WasmBool(this->toInt() >= other.toInt()); + Num res = WasmBool(this->toInt() >= other.toInt()); + debug_print("i32.ge_s", *this, other, res); + return res; } // i32.ge_u (Unsigned Greater Than or Equal): *this >= other (unsigned) inline Num i32_ge_u(const Num &other) const { - return WasmBool(this->toUInt() >= other.toUInt()); + Num res = WasmBool(this->toUInt() >= other.toUInt()); + debug_print("i32.ge_u", *this, other, res); + return res; } // i32.add (Wrapping addition) inline Num i32_add(const Num &other) const { uint32_t result_u = this->toUInt() + other.toUInt(); - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.add", *this, other, res); + return res; } // i32.sub (Wrapping subtraction) inline Num i32_sub(const Num &other) const { uint32_t result_u = this->toUInt() - other.toUInt(); - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.sub", *this, other, res); + return res; } // i32.mul (Wrapping multiplication) inline Num i32_mul(const Num &other) const { uint32_t result_u = this->toUInt() * other.toUInt(); - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.mul", *this, other, res); + return res; } // i32.div_s (Signed division with traps) @@ -101,14 +141,18 @@ struct Num { throw std::runtime_error("i32.div_s: Division by zero"); } - return Num(dividend / divisor); + Num res(dividend / divisor); + debug_print("i32.div_s", *this, other, res); + return res; } // i32.shl (Shift Left): *this << other (shift count masked by 31) inline Num i32_shl(const Num &other) const { uint32_t shift_amount = other.toUInt() & 0x1F; uint32_t result_u = toUInt() << shift_amount; - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.shl", *this, other, res); + return res; } // i32.shr_s (Signed Shift Right): *this >> other (Arithmetic shift) @@ -116,7 +160,9 @@ struct Num { // Wasm masks the shift amount by 31 (0x1F) uint32_t shift_amount = other.toUInt() & 0x1F; int32_t result_s = toInt() >> shift_amount; - return Num(result_s); + Num res(result_s); + debug_print("i32.shr_s", *this, other, res); + return res; } // i32.shr_u (Unsigned Shift Right): *this >>> other (Logical shift) @@ -124,13 +170,17 @@ struct Num { // Wasm masks the shift amount by 31 (0x1F) uint32_t shift_amount = other.toUInt() & 0x1F; uint32_t result_u = toUInt() >> shift_amount; - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.shr_u", *this, other, res); + return res; } // i32.and (Bitwise AND) inline Num i32_and(const Num &other) const { uint32_t result_u = this->toUInt() & other.toUInt(); - return Num(static_cast(result_u)); + Num res(static_cast(result_u)); + debug_print("i32.and", *this, other, res); + return res; } }; @@ -272,6 +322,10 @@ class Frames_t { void pushFrame(std::int32_t size) { assert(size >= 0); count += size; + // Zero-initialize the new stack frames. + for (std::int32_t i = 0; i < size; ++i) { + stack_ptr[count - 1 - i] = Num(0); + } } void reset() { count = 0; } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 43e991313..f51776577 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -777,7 +777,12 @@ inline bool NodeBox::fillIfElseNode(SymVal cond, int id) { } else if (dynamic_cast(node.get())) { node = std::make_unique(cond, this, id); return true; + } else if (dynamic_cast(node.get()) != nullptr) { + assert(false && + "Unexpected traversal: arrived at a node marked 'NotToExplore'."); + return false; } + assert( dynamic_cast(node.get()) != nullptr && "Current node is not an Unexplored nor an IfElseNode, cannot fill it!"); From 6744d1807c20f762f743a2ace57c1db0cf5d9a02 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 8 Nov 2025 16:45:27 -0500 Subject: [PATCH 080/105] use z3's api to evaluate a symbolic expression --- headers/wasm/concolic_driver.hpp | 16 +++- headers/wasm/smt_solver.hpp | 22 +++-- headers/wasm/symbolic_rt.hpp | 148 ++++++++++++++++++++++++------- 3 files changed, 146 insertions(+), 40 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index e9da77c1d..cb3a40c0c 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -96,7 +96,8 @@ inline void ConcolicDriver::main_exploration_loop() { node->fillUnreachableNode(); continue; } - auto new_env = result.value(); + auto &new_env = result.value().first; + auto &model = result.value().second; // update global symbolic environment from SMT solved model SymEnv.update(std::move(new_env)); @@ -104,7 +105,18 @@ inline void ConcolicDriver::main_exploration_loop() { GENSYM_INFO("Now execute the program with symbolic environment: "); GENSYM_INFO(SymEnv.to_string()); if (REUSE_SNAPSHOT) { - node->reach_here(entrypoint); + if (auto snapshot = dynamic_cast(node->node.get())) { + assert(REUSE_SNAPSHOT); + auto snap = snapshot->get_snapshot(); + std::cout << "Model \n" + << model << std::endl; + snap.resume_execution_by_model(node, model); + } else { + auto timer = ManagedTimer(TimeProfileKind::INSTR); + ExploreTree.reset_cursor(); + reset_stacks(); + entrypoint(); + } } else { auto timer = ManagedTimer(TimeProfileKind::INSTR); ExploreTree.reset_cursor(); diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 09c91e89f..e94e0ee1b 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -17,7 +17,8 @@ class Solver { public: Solver() {} - std::optional solve(std::vector &conditions) { + std::optional> + solve(std::vector &conditions) { z3::solver z3_solver(z3_ctx); z3::check_result solver_result; { @@ -50,13 +51,15 @@ class Solver { GENSYM_INFO("Find a variable that is not created by GenSym: " + name); } } - return result; + return std::optional>( + std::in_place, std::move(result), std::move(model)); } case z3::unknown: throw std::runtime_error("Z3 solver returned unknown status"); } return std::nullopt; // Should not reach here } + z3::expr build_z3_expr(SymVal &sym_val); private: z3::expr to_z3_conjunction(std::vector &conditions) { @@ -73,7 +76,6 @@ class Solver { } z3::context z3_ctx; - z3::expr build_z3_expr(SymVal &sym_val); z3::expr build_z3_expr_aux(SymVal &sym_val); }; @@ -158,14 +160,22 @@ inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { } inline z3::expr Solver::build_z3_expr(SymVal &sym_val) { - if (sym_val.z3_expr) { - return *sym_val.z3_expr; + if (sym_val.symptr->z3_expr()) { + return *sym_val.symptr->z3_expr(); } auto e = build_z3_expr_aux(sym_val); - sym_val.z3_expr = std::make_shared(e); + sym_val.symptr->update_z3_expr(e); return e; } +inline EvalRes eval_sym_expr_by_model(const SymVal &sym, z3::model &model) { + auto expr = solver.build_z3_expr(const_cast(sym)); + z3::expr value = model.eval(expr, false); + // every value is bitvector + int width = expr.get_sort().bv_size(); + return EvalRes(Num(value.get_numeral_int64()), width); +} + inline std::monostate GENSYM_SYM_ASSERT(SymVal &sym_cond) { std::vector conds = ExploreTree.collect_current_path_conds(); conds.push_back(sym_cond.negate()); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index f51776577..fefc126be 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -32,6 +32,11 @@ class Symbolic { Symbolic() {} virtual ~Symbolic() = default; // Make Symbolic polymorphic virtual int size() = 0; + virtual std::optional z3_expr() { return _z3_expr; } + virtual void update_z3_expr(z3::expr expr) { _z3_expr = expr; } + +private: + std::optional _z3_expr; }; static int max_id = 0; @@ -91,7 +96,6 @@ static std::shared_ptr ZeroByte = struct SymVal { std::shared_ptr symptr; - std::shared_ptr z3_expr; SymVal() : symptr(ZERO) {} SymVal(std::shared_ptr symptr) : symptr(symptr) {} @@ -147,20 +151,34 @@ struct SymExtract : Symbolic { SymVal value; int high; int low; + int size_cache = -1; SymExtract(SymVal value, int high, int low) : value(value), high(high), low(low) {} - int size() override { return 1 + value.size(); } + int size() override { + if (size_cache != -1) { + return size_cache; + } + size_cache = 1 + value.size(); + return size_cache; + } }; struct SymBinary : Symbolic { Operation op; SymVal lhs; SymVal rhs; + int size_cache = -1; SymBinary(Operation op, SymVal lhs, SymVal rhs) : op(op), lhs(lhs), rhs(rhs) {} - int size() override { return 1 + lhs.size() + rhs.size(); } + int size() override { + if (size_cache != -1) { + return size_cache; + } + size_cache = 1 + lhs.size() + rhs.size(); + return size_cache; + } }; inline SymVal SymVal::add(const SymVal &other) const { @@ -517,6 +535,8 @@ class Snapshot_t { SymMemory_t get_memory() const { return memory; } std::monostate resume_execution(NodeBox *node) const; + std::monostate resume_execution_by_model(NodeBox *node, + z3::model &model) const; static int cost_of_snapshot(); @@ -527,6 +547,7 @@ class Snapshot_t { // The continuation at the snapshot point Cont_t cont; MCont_t mcont; + void restore_states_to_global() const; }; static SymFrames_t SymFrames; @@ -899,7 +920,10 @@ inline int Snapshot_t::cost_of_snapshot() { auto cost_of_stack_copy = SymStack.cost_of_copy(); auto cost_of_frame_copy = SymFrames.cost_of_copy(); auto cost_of_memory_copy = SymMemory.cost_of_copy(); - return 5.336 * + // The speed ratio between symbolic expression instantiation and WebAssembly + // instruction execution, given by benchmark results + auto ratio = 5.336; + return ratio * (cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy); } @@ -968,22 +992,16 @@ class ExploreTree_t { bool worth_to_create_snapshot() { if (!ENABLE_COST_MODEL) { + // If we are not using cost model, always create snapshot return REUSE_SNAPSHOT; } // find out the best way to reach the current position via our cost model auto snapshot_cost = Snapshot_t::cost_of_snapshot(); - int reach_parent_cost = 0; - if (cursor->parent) { - reach_parent_cost = cursor->parent->min_cost_of_reaching_here(); - } else { - reach_parent_cost = 0; + int re_execution_cost = cursor->instr_cost; + if (snapshot_cost <= re_execution_cost) { + GENSYM_INFO("Snapshot is worth to create"); } - auto parent_cost = - cursor->parent ? cursor->parent->min_cost_of_reaching_here() : 0; - auto exec_from_parent_cost = reach_parent_cost + cursor->instr_cost; - GENSYM_INFO("The score of snapshot tendency: " + - std::to_string(exec_from_parent_cost - snapshot_cost)); - return snapshot_cost <= exec_from_parent_cost; + return snapshot_cost <= re_execution_cost; } std::monostate moveCursor(bool branch, Control control) { @@ -994,7 +1012,9 @@ class ExploreTree_t { if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); int cost_from_parent = CostManager.dump_instr_cost(); - cursor->instr_cost = cost_from_parent; + int cost_from_root = + cost_from_parent + (cursor->parent ? cursor->parent->instr_cost : 0); + cursor->instr_cost = cost_from_root; if (branch) { true_branch_cov_map[if_else_node->id] = true; if (worth_to_create_snapshot()) { @@ -1026,7 +1046,9 @@ class ExploreTree_t { if_else_node != nullptr && "Can't move cursor when the branch node is not initialized correctly!"); int cost_from_parent = CostManager.dump_instr_cost(); - cursor->instr_cost = cost_from_parent; + int cost_from_root = + cost_from_parent + (cursor->parent ? cursor->parent->instr_cost : 0); + cursor->instr_cost = cost_from_root; if (branch) { true_branch_cov_map[if_else_node->id] = true; if_else_node->false_branch->fillNotToExploreNode(); @@ -1343,6 +1365,8 @@ static EvalRes eval_sym_expr(const SymVal &sym, SymEnv_t &sym_env) { throw std::runtime_error("Not supported symbolic expression"); } +inline EvalRes eval_sym_expr_by_model(const SymVal &sym, z3::model &model); + static void resume_conc_stack(const SymStack_t &sym_stack, Stack_t &stack, SymEnv_t &sym_env) { stack.resize(sym_stack.size()); @@ -1354,8 +1378,21 @@ static void resume_conc_stack(const SymStack_t &sym_stack, Stack_t &stack, } } +static void resume_conc_stack_by_model(const SymStack_t &sym_stack, + Stack_t &stack, z3::model &model) { + GENSYM_INFO("Restoring concrete stack from symbolic stack"); + stack.resize(sym_stack.size()); + for (size_t i = 0; i < sym_stack.size(); ++i) { + auto sym = sym_stack[i]; + auto res = eval_sym_expr_by_model(sym, model); + auto conc = res.value; + stack.set_from_front(i, conc); + } +} + static void resume_conc_frames(const SymFrames_t &sym_frame, Frames_t &frames, SymEnv_t &sym_env) { + GENSYM_INFO("Restoring concrete frames from symbolic frames"); frames.resize(sym_frame.size()); for (size_t i = 0; i < sym_frame.size(); ++i) { auto sym = sym_frame[i]; @@ -1366,8 +1403,22 @@ static void resume_conc_frames(const SymFrames_t &sym_frame, Frames_t &frames, } } +static void resume_conc_frames_by_model(const SymFrames_t &sym_frame, + Frames_t &frames, z3::model &model) { + GENSYM_INFO("Restoring concrete frames from symbolic frames"); + frames.resize(sym_frame.size()); + for (size_t i = 0; i < sym_frame.size(); ++i) { + auto sym = sym_frame[i]; + assert(sym.symptr != nullptr); + auto res = eval_sym_expr_by_model(sym, model); + auto conc = res.value; + frames.set_from_front(i, conc); + } +} + static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, SymEnv_t &sym_env) { + GENSYM_INFO("Restoring concrete memory from symbolic memory"); memory.reset(); for (const auto &pair : sym_memory.memory) { int32_t addr = pair.first; @@ -1380,6 +1431,21 @@ static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, } } +static void resume_conc_memory_by_model(const SymMemory_t &sym_memory, + Memory_t &memory, z3::model &model) { + GENSYM_INFO("Restoring concrete memory from symbolic memory"); + memory.reset(); + for (const auto &pair : sym_memory.memory) { + int32_t addr = pair.first; + SymVal sym = pair.second; + assert(sym.symptr != nullptr); + auto res = eval_sym_expr_by_model(sym, model); + auto conc = res.value; + assert(res.width == 8 && "Memory should only store bytes"); + memory.store_byte(addr, conc.value & 0xFF); + } +} + static void resume_conc_states(const SymStack_t &sym_stack, const SymFrames_t &sym_frame, const SymMemory_t &sym_memory, Stack_t &stack, @@ -1390,33 +1456,51 @@ static void resume_conc_states(const SymStack_t &sym_stack, resume_conc_memory(sym_memory, memory, sym_env); } -inline std::monostate Snapshot_t::resume_execution(NodeBox *node) const { - // Reset explore tree's cursor - ExploreTree.set_cursor(node); +static void resume_conc_states_by_model(const SymStack_t &sym_stack, + const SymFrames_t &sym_frame, + const SymMemory_t &sym_memory, + Stack_t &stack, Frames_t &frames, + Memory_t &memory, z3::model &model) { + resume_conc_stack_by_model(sym_stack, stack, model); + resume_conc_frames_by_model(sym_frame, frames, model); + resume_conc_memory_by_model(sym_memory, memory, model); +} +inline void Snapshot_t::restore_states_to_global() const { // Restore the symbolic state from the snapshot GENSYM_INFO("Reusing symbolic state from snapshot"); SymStack = stack; SymFrames = frames; SymMemory = memory; +} + +inline std::monostate +Snapshot_t::resume_execution_by_model(NodeBox *node, z3::model &model) const { + // Reset explore tree's cursor and restore symbolic states + ExploreTree.set_cursor(node); + restore_states_to_global(); + { auto timer = ManagedTimer(TimeProfileKind::RESUME_SNAPSHOT); // Restore the concrete states from the symbolic states - resume_conc_states(stack, frames, memory, Stack, Frames, Memory, SymEnv); + resume_conc_states_by_model(stack, frames, memory, Stack, Frames, Memory, + model); } - int sym_size = 0; + // Resume execution from the continuation + auto timer = ManagedTimer(TimeProfileKind::INSTR); + return cont(mcont); +} + +[[deprecated]] +inline std::monostate Snapshot_t::resume_execution(NodeBox *node) const { + // Reset explore tree's cursor and restore symbolic states + ExploreTree.set_cursor(node); + restore_states_to_global(); { - auto timer = ManagedTimer(TimeProfileKind::COUNT_SYM_SIZE); - for (size_t i = 0; i < stack.size(); ++i) { - sym_size += stack[i].size(); - } - for (size_t i = 0; i < frames.size(); ++i) { - sym_size += frames[i].size(); - } + auto timer = ManagedTimer(TimeProfileKind::RESUME_SNAPSHOT); + // Restore the concrete states from the symbolic states + resume_conc_states(stack, frames, memory, Stack, Frames, Memory, SymEnv); } - std::cout << "[Info] Resumed symbolic execution from snapshot, total " - "symbolic expression and frame size: " - << sym_size << std::endl; // Resume execution from the continuation auto timer = ManagedTimer(TimeProfileKind::INSTR); From 5f6566920e3c0b4801f27d6adae4f5acef2dd1a8 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 8 Nov 2025 16:58:04 -0500 Subject: [PATCH 081/105] let z3 decide the value of symbols that are not in the model --- headers/wasm/smt_solver.hpp | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index e94e0ee1b..a34ab6d3e 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -170,7 +170,8 @@ inline z3::expr Solver::build_z3_expr(SymVal &sym_val) { inline EvalRes eval_sym_expr_by_model(const SymVal &sym, z3::model &model) { auto expr = solver.build_z3_expr(const_cast(sym)); - z3::expr value = model.eval(expr, false); + // let z3 decide the value of symbols that are not in the model + z3::expr value = model.eval(expr, true); // every value is bitvector int width = expr.get_sort().bv_size(); return EvalRes(Num(value.get_numeral_int64()), width); From 48948294026215b17ba265b31c9c6c848891c777 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Sat, 8 Nov 2025 17:10:47 -0500 Subject: [PATCH 082/105] tweak tests --- headers/wasm/concrete_rt.hpp | 1 + .../genwasym/TestStagedConcolicEval.scala | 25 ++++++++++++------- src/test/scala/genwasym/TestStagedEval.scala | 16 ++++++++---- 3 files changed, 28 insertions(+), 14 deletions(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 4a2d4ad58..852570eff 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -265,6 +265,7 @@ class Stack_t { for (int32_t i = 0; i < count; ++i) { std::cout << stack_ptr[count - i - 1].value << std::endl; } + std::cout << "End of Stack contents" << std::endl; } void initialize() { diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index d1590f6a0..f58f2c6b9 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -73,11 +73,17 @@ class TestStagedConcolicEval extends FunSuite { println(result) expect.map(vs => { - val stackValues = result - .split("Stack contents: \n")(1) - .split("\n") - .map(_.toFloat) - .toList + val stackValues = { + val startMarker = "Stack contents: \n" + val endMarker = "End of Stack contents" + val start = result.indexOf(startMarker) + val end = if (start >= 0) result.indexOf(endMarker, start + startMarker.length) else -1 + require(start >= 0 && end >= 0, s"Could not find markers '$startMarker' and '$endMarker' in output") + result.substring(start + startMarker.length, end).trim + .split("\n") + .map(_.toFloat) + .toList + } assert(vs == stackValues) }) } @@ -113,10 +119,11 @@ class TestStagedConcolicEval extends FunSuite { } test("btree-bug-finding-concolic") { testFileConcolicCpp("./benchmarks/wasm/btree/2o1u-unlabeled.wat", exitByCoverage = true) } - test("long-trivial-execution-concrete") { - // This is a example to show how much performance improvement we can get by immutable data structure - testFileConcreteCpp("./benchmarks/wasm/staged/long-trivial-execution.wat", None) - } + // Don't run this test by default since it takes too long and is only for performance comparison + // test("long-trivial-execution-concrete") { + // // This is a example to show how much performance improvement we can get by immutable data structure + // testFileConcreteCpp("./benchmarks/wasm/staged/long-trivial-execution.wat", None) + // } test("return-poly - concrete") { testFileConcreteCpp("./benchmarks/wasm/staged/return_poly.wat", Some("$real_main"), expect=Some(List(42))) diff --git a/src/test/scala/genwasym/TestStagedEval.scala b/src/test/scala/genwasym/TestStagedEval.scala index 3769428f4..ec7c43bed 100644 --- a/src/test/scala/genwasym/TestStagedEval.scala +++ b/src/test/scala/genwasym/TestStagedEval.scala @@ -36,11 +36,17 @@ class TestStagedEval extends FunSuite { println(result) expect.map(vs => { - val stackValues = result - .split("Stack contents: \n")(1) - .split("\n") - .map(_.toFloat) - .toList + val stackValues = { + val startMarker = "Stack contents: \n" + val endMarker = "End of Stack contents" + val start = result.indexOf(startMarker) + val end = if (start >= 0) result.indexOf(endMarker, start + startMarker.length) else -1 + require(start >= 0 && end >= 0, s"Could not find markers '$startMarker' and '$endMarker' in output") + result.substring(start + startMarker.length, end).trim + .split("\n") + .map(_.toFloat) + .toList + } assert(vs == stackValues) }) } From da5efc8a85167a3ba211bd2fecde8ec3905ad045 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 10 Nov 2025 04:25:16 -0500 Subject: [PATCH 083/105] update test script --- benchmarks/pldi2026/btree/collect_result.py | 132 ++++++++++++++++++++ benchmarks/pldi2026/btree/compile.py | 63 ++++++++-- benchmarks/pldi2026/btree/run.py | 84 ++++++++++++- 3 files changed, 268 insertions(+), 11 deletions(-) create mode 100644 benchmarks/pldi2026/btree/collect_result.py diff --git a/benchmarks/pldi2026/btree/collect_result.py b/benchmarks/pldi2026/btree/collect_result.py new file mode 100644 index 000000000..3babd7354 --- /dev/null +++ b/benchmarks/pldi2026/btree/collect_result.py @@ -0,0 +1,132 @@ +import csv +from dataclasses import dataclass +import json +from pathlib import Path + + +@dataclass +class BenchmarkResult: + instr_time: float + solver_time: float + resuming_time: float + total_time: float + total_no_solver_time: float + cost_model_time: float + path_count: int + + +def read_json_output(file_path) -> BenchmarkResult: + with open(file_path, "r") as f: + data = json.load(f) + instr_time = data.get("profile_summary").get("total_time_instruction_execution_s") + solver_time = data.get("profile_summary").get("total_time_solver_s") + resuming_time = data.get("profile_summary").get( + "total_time_resuming_from_snapshot_s" + ) + cost_model_time = data.get("profile_summary").get( + "total_time_counting_symbolic_size_s" + ) + path_count = data.get("finished_count") + return BenchmarkResult( + instr_time=instr_time, + solver_time=solver_time, + resuming_time=resuming_time, + total_time=instr_time + solver_time + resuming_time + cost_model_time, + total_no_solver_time=resuming_time + instr_time, + cost_model_time=cost_model_time, + path_count=path_count, + ) + + +def read_json_output_for_dir(directory_path) -> dict[str, BenchmarkResult]: + result = dict() + for json_file in directory_path.glob("**/*.json"): + parent_dir = json_file.parent + benchmark_name = parent_dir.name.split(".")[0] + benchmark_result = read_json_output(json_file) + result[benchmark_name] = benchmark_result + return result + + +def entry(): + current_dir = Path(__file__).parent + NoConfig_dir = current_dir / "NoConfig" + Snapshot_dir = current_dir / "Snapshot" + no_config_result = read_json_output_for_dir(NoConfig_dir) + snapshot_result = read_json_output_for_dir(Snapshot_dir) + all_configs = set(no_config_result.keys()).union(set(snapshot_result.keys())) + output_csv = current_dir / "benchmark_results.csv" + with open(output_csv, "w", newline="") as csvfile: + fieldnames = [ + "Benchmark", + "NoConfig_InstrTime(s)", + "NoConfig_SolverTime(s)", + "NoConfig_ResumingTime(s)", + "NoConfig_CostModelTime(s)", + "NoConfig_TotalTime(s)", + "NoConfig_PathCount", + "Snapshot_InstrTime(s)", + "Snapshot_NoSolverTime(s)", + "Snapshot_SolverTime(s)", + "Snapshot_ResumingTime(s)", + "Snapshot_CostModelTime(s)", + "Snapshot_TotalTime(s)", + "Snapshot_PathCount", + ] + writer = csv.DictWriter(csvfile, fieldnames=fieldnames) + writer.writeheader() + for benchmark in sorted(all_configs): + no_config = no_config_result.get(benchmark) + snapshot = snapshot_result.get(benchmark) + row = {"Benchmark": benchmark} + if no_config: + row.update( + { + "NoConfig_InstrTime(s)": no_config.instr_time, + "NoConfig_SolverTime(s)": no_config.solver_time, + "NoConfig_ResumingTime(s)": no_config.resuming_time, + "NoConfig_CostModelTime(s)": no_config.cost_model_time, + "NoConfig_TotalTime(s)": no_config.total_time, + "NoConfig_PathCount": no_config.path_count, + } + ) + else: + row.update( + { + "NoConfig_InstrTime(s)": "x", + "NoConfig_SolverTime(s)": "x", + "NoConfig_ResumingTime(s)": "x", + "NoConfig_CostModelTime(s)": "x", + "NoConfig_TotalTime(s)": "x", + "NoConfig_PathCount": "x", + } + ) + if snapshot: + row.update( + { + "Snapshot_InstrTime(s)": snapshot.instr_time, + "Snapshot_NoSolverTime(s)": snapshot.total_no_solver_time, + "Snapshot_SolverTime(s)": snapshot.solver_time, + "Snapshot_ResumingTime(s)": snapshot.resuming_time, + "Snapshot_CostModelTime(s)": snapshot.cost_model_time, + "Snapshot_TotalTime(s)": snapshot.total_time, + "Snapshot_PathCount": snapshot.path_count, + } + ) + else: + row.update( + { + "Snapshot_InstrTime(s)": "x", + "Snapshot_NoSolverTime(s)": "x", + "Snapshot_SolverTime(s)": "x", + "Snapshot_ResumingTime(s)": "x", + "Snapshot_CostModelTime(s)": "x", + "Snapshot_TotalTime(s)": "x", + "Snapshot_PathCount": "x", + } + ) + writer.writerow(row) + + +if __name__ == "__main__": + entry() diff --git a/benchmarks/pldi2026/btree/compile.py b/benchmarks/pldi2026/btree/compile.py index 5e1555b31..f31540b2b 100644 --- a/benchmarks/pldi2026/btree/compile.py +++ b/benchmarks/pldi2026/btree/compile.py @@ -14,7 +14,7 @@ print(f"No .cpp files found in {HERE}") sys.exit(0) -DEFAULT_FLAGS = [ +BASE_FLAGS = [ "-std=c++17", "-g", "-O3", @@ -24,11 +24,18 @@ "-I/home/zdh/WorkSpace/GenSym/headers", "-lz3", "-DENABLE_PROFILE_TIME", + "-DNO_INFO" +] + +TOOL_CONFIG_DEFAULT = [ "-DNO_REUSE", ] +TOOL_CONFIG_SNAPSHOT_UNIFORMLY = [] +TOOL_CONFIG_SNAPSHOT_COST_MODEL = ["-DUSE_COST_MODEL"] EXTRA_FLAGS = sys.argv[1:] -FLAGS = DEFAULT_FLAGS + EXTRA_FLAGS - +FLAGS = BASE_FLAGS + TOOL_CONFIG_DEFAULT + EXTRA_FLAGS +SNAPSHOT_FLAGS = BASE_FLAGS + TOOL_CONFIG_SNAPSHOT_UNIFORMLY + EXTRA_FLAGS +SNAPSHOT_COST_MODEL_FLAGS = BASE_FLAGS + TOOL_CONFIG_SNAPSHOT_COST_MODEL + EXTRA_FLAGS def compile_all(cpp_files=None, flags=None): if cpp_files is None: @@ -52,17 +59,55 @@ def compile_all(cpp_files=None, flags=None): print("Error: g++ not found. Install a C++ compiler.") sys.exit(1) + snapshot_out = cpp.with_suffix(".snapshot.exe") + snapshot_cmd = ["g++", str(cpp), "-o", str(snapshot_out)] + SNAPSHOT_FLAGS + print("Compiling snapshot version:", cpp.name) + try: + print(" Executing command:") + print(" ", " ".join(snapshot_cmd)) + snapshot_proc = subprocess.run(snapshot_cmd, capture_output=True, text=True) + except FileNotFoundError: + print("Error: g++ not found. Install a C++ compiler.") + sys.exit(1) + + snapshot_cost_model_out = cpp.with_suffix(".costmodel.exe") + snapshot_cost_model_cmd = ["g++", str(cpp), "-o", str(snapshot_cost_model_out)] + SNAPSHOT_COST_MODEL_FLAGS + print("Compiling snapshot cost model version:", cpp.name) + try: + print(" Executing command:") + print(" ", " ".join(snapshot_cost_model_cmd)) + snapshot_cost_model_proc = subprocess.run(snapshot_cost_model_cmd, capture_output=True, text=True) + except FileNotFoundError: + print("Error: g++ not found. Install a C++ compiler.") + sys.exit(1) + compiled_total += 1 + + if snapshot_proc.returncode == 0: + print(f" Successfully compiled snapshot {cpp.name} to {snapshot_out.name}") + else: + print(f" Failed to compile snapshot {cpp.name}") + print(" Compiler output:") + print(snapshot_proc.stdout) + print(snapshot_proc.stderr) + if proc.returncode == 0: + print(f" Successfully compiled {cpp.name} to {out.name}") compiled_success += 1 - print(" -> OK:", out.name) else: + print(f" Failed to compile {cpp.name}") + print(" Compiler output:") + print(proc.stdout) + print(proc.stderr) compiled_failed += 1 - print(" -> FAILED:", cpp.name) - if proc.stdout: - print(proc.stdout.strip()) - if proc.stderr: - print(proc.stderr.strip()) + + if snapshot_cost_model_proc.returncode == 0: + print(f" Successfully compiled snapshot cost model {cpp.name} to {snapshot_cost_model_out.name}") + else: + print(f" Failed to compile snapshot cost model {cpp.name}") + print(" Compiler output:") + print(snapshot_cost_model_proc.stdout) + print(snapshot_cost_model_proc.stderr) print() print("Overall summary:") diff --git a/benchmarks/pldi2026/btree/run.py b/benchmarks/pldi2026/btree/run.py index b462af292..8f492488d 100644 --- a/benchmarks/pldi2026/btree/run.py +++ b/benchmarks/pldi2026/btree/run.py @@ -16,14 +16,32 @@ def is_executable(path: Path) -> bool: # executable bit or .exe suffix return os.access(str(path), os.X_OK) or path.suffix.lower() == ".exe" +def is_snapshot_executable(path: Path) -> bool: + if not path.is_file(): + return False + + return path.name.endswith(".snapshot.exe") + +def is_cost_model_executable(path: Path) -> bool: + if not path.is_file(): + return False + + return path.name.endswith(".costmodel.exe") def run_all(targets: list[Path], action): for file_path in targets: if not is_executable(file_path): continue file_name = file_path.name.removesuffix(".exe") - output_path = f"{file_name}.output" + if is_snapshot_executable(file_path): + output_path = "Snapshot" + f"/{file_name}.output" + elif is_cost_model_executable(file_path): + output_path = "CostModel" + f"/{file_name}.output" + else: + output_path = "NoConfig" + f"/{file_name}.output" + if Path(output_path).exists(): + print(f"Output path {output_path} already exists, skipping...") continue if action == "run": env = os.environ.copy() @@ -64,7 +82,69 @@ def main(): parser.print_help() return 0 - targets = list(sorted(list(Path(".").iterdir()))) + # targets = list(sorted(list(Path(".").iterdir()))) + targets = list(map(Path, [ + "2o1u.wat.exe", + "2o1u.wat.snapshot.exe", + "2o1u.wat.costmodel.exe", + "3o1u.wat.exe", + "3o1u.wat.snapshot.exe", + "3o1u.wat.costmodel.exe", + "4o1u.wat.exe", + "4o1u.wat.snapshot.exe", + "4o1u.wat.costmodel.exe", + "5o1u.wat.exe", + "5o1u.wat.snapshot.exe", + "5o1u.wat.costmodel.exe", + "6o1u.wat.exe", + "6o1u.wat.snapshot.exe", + "6o1u.wat.costmodel.exe", + "7o1u.wat.exe", + "7o1u.wat.snapshot.exe", + "7o1u.wat.costmodel.exe", + "8o1u.wat.exe", + "8o1u.wat.snapshot.exe", + "8o1u.wat.costmodel.exe", + "9o1u.wat.exe", + "9o1u.wat.snapshot.exe", + "9o1u.wat.costmodel.exe", + "2o2u.wat.exe", + "2o2u.wat.snapshot.exe", + "2o2u.wat.costmodel.exe", + "3o2u.wat.exe", + "3o2u.wat.snapshot.exe", + "3o2u.wat.costmodel.exe", + "4o2u.wat.exe", + "4o2u.wat.snapshot.exe", + "4o2u.wat.costmodel.exe", + "5o2u.wat.exe", + "5o2u.wat.snapshot.exe", + "5o2u.wat.costmodel.exe", + "6o2u.wat.exe", + "6o2u.wat.snapshot.exe", + "6o2u.wat.costmodel.exe", + "7o2u.wat.exe", + "7o2u.wat.snapshot.exe", + "7o2u.wat.costmodel.exe", + # "8o2u.wat.exe" is not runnable even in wasp + # "9o2u.wat.exe", + "3o3u.wat.exe", + "3o3u.wat.snapshot.exe", + "3o3u.wat.costmodel.exe", + "4o3u.wat.exe", + "4o3u.wat.snapshot.exe", + "4o3u.wat.costmodel.exe", + "5o3u.wat.exe", + "5o3u.wat.snapshot.exe", + "5o3u.wat.costmodel.exe", + "6o3u.wat.exe", + "6o3u.wat.snapshot.exe", + "6o3u.wat.costmodel.exe", + "7o3u.wat.exe", + "7o3u.wat.snapshot.exe", + "7o3u.wat.costmodel.exe", + ])) + print(targets) if args.run_all: run_all(targets, action="run") elif args.clean: From 9d2d23b6cc17ae60f3534a2dbff32e9bac9ddd60 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Mon, 10 Nov 2025 15:41:43 -0500 Subject: [PATCH 084/105] support some f32 --- benchmarks/wasm/f32_test.wat | 24 ++ .../scala/wasm/StagedConcolicMiniWasm.scala | 280 +++++++++++++----- .../genwasym/TestStagedConcolicEval.scala | 4 + 3 files changed, 237 insertions(+), 71 deletions(-) create mode 100644 benchmarks/wasm/f32_test.wat diff --git a/benchmarks/wasm/f32_test.wat b/benchmarks/wasm/f32_test.wat new file mode 100644 index 000000000..b1a03b5d4 --- /dev/null +++ b/benchmarks/wasm/f32_test.wat @@ -0,0 +1,24 @@ +(module + (type (;0;) (func (result f32 f32 f32 f32 i32))) + (func (;0;) (type 0) (result f32 f32 f32 f32 i32) + (local f32 f32) + f32.const 0x1.cp+1 (;=3.5;) + local.set 0 + f32.const 0x1p+1 (;=2;) + local.set 1 + local.get 0 + local.get 1 + f32.add + local.get 0 + local.get 1 + f32.sub + local.get 0 + local.get 1 + f32.mul + local.get 0 + local.get 1 + f32.div + local.get 0 + local.get 1 + f32.gt) + (export "test_f32" (func 0))) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 48d902801..ce00c3d77 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -617,8 +617,9 @@ trait StagedWasmEvaluator extends SAIOps { // case ShrS(_) => v1 >> v2 // TODO: signed shift right case ShrU(_) => v1 >> v2 case And(_) => v1 & v2 - case DivS(_) => v1 / v2 - case DivU(_) => v1 / v2 + case DivS(_) => v1 divs v2 + case DivU(_) => v1 divu v2 + case Div(_) => v1 div v2 case _ => throw new Exception(s"Unknown binary operation $op") } @@ -631,8 +632,9 @@ trait StagedWasmEvaluator extends SAIOps { // case ShrS(_) => v1 >> v2 // TODO: signed shift right case ShrU(_) => v1 >> v2 case And(_) => v1 & v2 - case DivS(_) => v1 / v2 - case DivU(_) => v1 / v2 + case DivS(_) => v1 divs v2 + case DivU(_) => v1 divu v2 + case Div(_) => v1 div v2 case _ => throw new Exception(s"Unknown binary operation $op") } @@ -648,6 +650,10 @@ trait StagedWasmEvaluator extends SAIOps { case LeU(_) => v1 leu v2 case GeS(_) => v1 >= v2 case GeU(_) => v1 geu v2 + case Lt(_) => v1 lt v2 + case Le(_) => v1 le v2 + case Gt(_) => v1 gt v2 + case Ge(_) => v1 ge v2 case _ => ??? } @@ -662,6 +668,10 @@ trait StagedWasmEvaluator extends SAIOps { case LeU(_) => v1 leu v2 case GeS(_) => v1 >= v2 case GeU(_) => v1 geu v2 + case Lt(_) => v1 lt v2 + case Le(_) => v1 le v2 + case Gt(_) => v1 gt v2 + case Ge(_) => v1 ge v2 case _ => ??? } @@ -988,178 +998,228 @@ trait StagedWasmEvaluator extends SAIOps { def +(rhs: StagedConcreteNum): StagedConcreteNum = (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-add".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-add".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-add".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-add".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-add".reflectCtrlWith[Num](num.i, rhs.i)) } def -(rhs: StagedConcreteNum): StagedConcreteNum = (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-sub".reflectCtrlWith[Num](num.i, rhs.i)) } def *(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-mul".reflectCtrlWith[Num](num.i, rhs.i)) } } - def /(rhs: StagedConcreteNum): StagedConcreteNum = { + def divs(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-div".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def divu(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "i32-binary-div-u".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(I64Type), NumType(I64Type)) => + StagedConcreteNum(NumType(I64Type), "i64-binary-div-u".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def div(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-div".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-div".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-div".reflectCtrlWith[Num](num.i, rhs.i)) } } def <<(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-shl".reflectCtrlWith[Num](num.i, rhs.i)) } } def >>(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-shr".reflectCtrlWith[Num](num.i, rhs.i)) } } def &(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-binary-and".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I64Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I64Type), "i64-binary-and".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F32Type), NumType(F32Type)) => - StagedConcreteNum(NumType(F32Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F32Type), "f32-binary-and".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(F64Type), NumType(F64Type)) => - StagedConcreteNum(NumType(F64Type), "binary-and".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(F64Type), "f64-binary-and".reflectCtrlWith[Num](num.i, rhs.i)) } } def numEq(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-eq".reflectCtrlWith[Num](num.i, rhs.i)) } } def numNe(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-ne".reflectCtrlWith[Num](num.i, rhs.i)) } } def <(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-lts".reflectCtrlWith[Num](num.i, rhs.i)) } } def ltu(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-ltu".reflectCtrlWith[Num](num.i, rhs.i)) } } def >(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) } } def gtu(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-gtu".reflectCtrlWith[Num](num.i, rhs.i)) } } def <=(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-les".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-les".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-les".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-les".reflectCtrlWith[Num](num.i, rhs.i)) } } def leu(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-leu".reflectCtrlWith[Num](num.i, rhs.i)) } } def >=(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-ges".reflectCtrlWith[Num](num.i, rhs.i)) } } def geu(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => - StagedConcreteNum(NumType(I32Type), "relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i32-relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) case (NumType(I64Type), NumType(I64Type)) => - StagedConcreteNum(NumType(I32Type), "relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) + StagedConcreteNum(NumType(I32Type), "i64-relation-geu".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def lt(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(I32Type), "f32-relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(I32Type), "f64-relation-lt".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def le(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(I32Type), "f32-relation-le".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(I32Type), "f64-relation-le".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def gt(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(I32Type), "f32-relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(I32Type), "f64-relation-gt".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + + def ge(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedConcreteNum(NumType(I32Type), "f32-relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) + case (NumType(F64Type), NumType(F64Type)) => + StagedConcreteNum(NumType(I32Type), "f64-relation-ge".reflectCtrlWith[Num](num.i, rhs.i)) } } } @@ -1241,6 +1301,33 @@ trait StagedWasmEvaluator extends SAIOps { } } + def divs(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + + def divu(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-div-u".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(I64Type), NumType(I64Type)) => + StagedSymbolicNum(NumType(I64Type), "sym-binary-div-u".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + + def div(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(F32Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(F64Type), "sym-binary-div".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + def <<(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => @@ -1369,8 +1456,43 @@ trait StagedWasmEvaluator extends SAIOps { StagedSymbolicNum(NumType(I32Type), "sym-relation-geu".reflectCtrlWith[SymVal](num.s, rhs.s)) } } - } + def lt(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-lt".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + + def le(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-le".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + + def gt(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gt".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-gt".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + + def ge(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(F32Type), NumType(F32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) + case (NumType(F64Type), NumType(F64Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-relation-ge".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + } implicit class SymbolicOps(s: Rep[SymVal]) { def not(): Rep[SymVal] = { "sym-not".reflectCtrlWith(s) @@ -1513,40 +1635,56 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("(0 == "); shallow(num); emit(")") case Node(_, "sym-is-zero", List(s_num), _) => shallow(s_num); emit(".is_zero()") - case Node(_, "binary-add", List(lhs, rhs), _) => + case Node(_, "i32-binary-add", List(lhs, rhs), _) => shallow(lhs); emit(".i32_add("); shallow(rhs); emit(")") - case Node(_, "binary-sub", List(lhs, rhs), _) => + case Node(_, "i32-binary-sub", List(lhs, rhs), _) => shallow(lhs); emit(".i32_sub("); shallow(rhs); emit(")") - case Node(_, "binary-mul", List(lhs, rhs), _) => + case Node(_, "i32-binary-mul", List(lhs, rhs), _) => shallow(lhs); emit(".i32_mul("); shallow(rhs); emit(")") - case Node(_, "binary-div", List(lhs, rhs), _) => + case Node(_, "i32-binary-div", List(lhs, rhs), _) => shallow(lhs); emit(".i32_div_s("); shallow(rhs); emit(")") - case Node(_, "binary-shl", List(lhs, rhs), _) => + case Node(_, "i32-binary-shl", List(lhs, rhs), _) => shallow(lhs); emit(".i32_shl("); shallow(rhs); emit(")") - case Node(_, "binary-shr", List(lhs, rhs), _) => + case Node(_, "i32-binary-shr", List(lhs, rhs), _) => shallow(lhs); emit(".i32_shr("); shallow(rhs); emit(")") - case Node(_, "binary-and", List(lhs, rhs), _) => + case Node(_, "i32-binary-and", List(lhs, rhs), _) => shallow(lhs); emit(".i32_and("); shallow(rhs); emit(")") - case Node(_, "relation-eq", List(lhs, rhs), _) => + case Node(_, "i32-relation-eq", List(lhs, rhs), _) => shallow(lhs); emit(".i32_eq("); shallow(rhs); emit(")") - case Node(_, "relation-ne", List(lhs, rhs), _) => + case Node(_, "i32-relation-ne", List(lhs, rhs), _) => shallow(lhs); emit(".i32_ne("); shallow(rhs); emit(")") - case Node(_, "relation-lts", List(lhs, rhs), _) => + case Node(_, "i32-relation-lts", List(lhs, rhs), _) => shallow(lhs); emit(".i32_lt_s("); shallow(rhs); emit(")") - case Node(_, "relation-ltu", List(lhs, rhs), _) => + case Node(_, "i32-relation-ltu", List(lhs, rhs), _) => shallow(lhs); emit(".i32_lt_u("); shallow(rhs); emit(")") - case Node(_, "relation-gt", List(lhs, rhs), _) => + case Node(_, "i32-relation-gt", List(lhs, rhs), _) => shallow(lhs); emit(".i32_gt_s("); shallow(rhs); emit(")") - case Node(_, "relation-gtu", List(lhs, rhs), _) => + case Node(_, "i32-relation-gtu", List(lhs, rhs), _) => shallow(lhs); emit(".i32_gt_u("); shallow(rhs); emit(")") - case Node(_, "relation-les", List(lhs, rhs), _) => + case Node(_, "i32-relation-les", List(lhs, rhs), _) => shallow(lhs); emit(".i32_le_s("); shallow(rhs); emit(")") - case Node(_, "relation-leu", List(lhs, rhs), _) => + case Node(_, "i32-relation-leu", List(lhs, rhs), _) => shallow(lhs); emit(".i32_le_u("); shallow(rhs); emit(")") - case Node(_, "relation-ges", List(lhs, rhs), _) => + case Node(_, "i32-relation-ges", List(lhs, rhs), _) => shallow(lhs); emit(".i32_ge_s("); shallow(rhs); emit(")") - case Node(_, "relation-geu", List(lhs, rhs), _) => + case Node(_, "i32-relation-geu", List(lhs, rhs), _) => shallow(lhs); emit(".i32_ge_u("); shallow(rhs); emit(")") + case Node(_, "f32-binary-add", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_add("); shallow(rhs); emit(")") + case Node(_, "f32-binary-sub", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_sub("); shallow(rhs); emit(")") + case Node(_, "f32-binary-mul", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_mul("); shallow(rhs); emit(")") + case Node(_, "f32-binary-div", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_div("); shallow(rhs); emit(")") + case Node(_, "f32-relation-gt", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_gt("); shallow(rhs); emit(")") + case Node(_, "f32-relation-lt", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_lt("); shallow(rhs); emit(")") + case Node(_, "f32-relation-le", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_le("); shallow(rhs); emit(")") + case Node(_, "f32-relation-ge", List(lhs, rhs), _) => + shallow(lhs); emit(".f32_ge("); shallow(rhs); emit(")") case Node(_, "sym-binary-add", List(lhs, rhs), _) => shallow(lhs); emit(".add("); shallow(rhs); emit(")") case Node(_, "sym-binary-sub", List(lhs, rhs), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index f58f2c6b9..2e10bf72a 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -186,6 +186,10 @@ class TestStagedConcolicEval extends FunSuite { testFileConcreteCpp("./benchmarks/wasm/compare_wasp/small-snapshot.wat", Some("main")) } + test("f32-operations-concrete") { + testFileConcreteCpp("./benchmarks/wasm/f32_test.wat", Some("test_f32")) + } + // test("diverge") { // testFileConcolicCpp("./benchmarks/wasm/diverge.wat", Some("main")) // } From 3a7bdd7c27cf7e20c25b429278f7110d19738f55 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 00:55:41 -0500 Subject: [PATCH 085/105] support call_indirect --- benchmarks/wasm/call_indirect_test.wat | 25 + grammar/WatParser.g4 | 7 +- headers/wasm/concrete_rt.hpp | 277 ++- headers/wasm/controls.hpp | 2 + headers/wasm/symbolic_rt.hpp | 148 +- src/main/java/wasm/WatParser.java | 1730 ++++++++--------- src/main/scala/wasm/AST.scala | 2 +- src/main/scala/wasm/Parser.scala | 16 + .../scala/wasm/StagedConcolicMiniWasm.scala | 112 +- .../genwasym/TestStagedConcolicEval.scala | 4 + 10 files changed, 1358 insertions(+), 965 deletions(-) create mode 100644 benchmarks/wasm/call_indirect_test.wat diff --git a/benchmarks/wasm/call_indirect_test.wat b/benchmarks/wasm/call_indirect_test.wat new file mode 100644 index 000000000..7cf7c6b3a --- /dev/null +++ b/benchmarks/wasm/call_indirect_test.wat @@ -0,0 +1,25 @@ +(module + (type (;0;) (func (param i32) (result i32))) + (type (;1;) (func (param i32 i32) (result i32))) + (type (;2;) (func (result i32))) + (func (;0;) (type 0) (param i32) (result i32) + local.get 0 + i32.const 1 + i32.add) + (func (;1;) (type 0) (param i32) (result i32) + local.get 0 + i32.const 2 + i32.mul) + (func (;2;) (type 1) (param i32 i32) (result i32) + local.get 1 + local.get 0 + call_indirect (type 0)) + (func (;3;) (type 2) (result i32) + i32.const 0 + i32.const 41 + call 2) + (table (;0;) 2 funcref) + (export "run" (func 3)) + (export "dispatch" (func 2)) + (elem (;0;) (i32.const 0) func 0 1) + (start 3)) diff --git a/grammar/WatParser.g4 b/grammar/WatParser.g4 index 96ad2133b..99acf8b75 100644 --- a/grammar/WatParser.g4 +++ b/grammar/WatParser.g4 @@ -323,10 +323,11 @@ offset // TBH I'm not even sure what the `func 1` should count as // TODO: align with the rules here: // https://webassembly.github.io/function-references/core/_download/WebAssembly.pdf +// For now, only support initialize one table via function indices elem - : LPAR ELEM idx? LPAR instr RPAR idx* RPAR - | LPAR ELEM idx? offset idx* RPAR - | LPAR ELEM idx? DECLARE FUNC idx* RPAR + : LPAR ELEM LPAR instr RPAR FUNC idx* RPAR + // | LPAR ELEM idx? offset idx* RPAR + // | LPAR ELEM idx? DECLARE FUNC idx* RPAR ; table diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 852570eff..f991fc58f 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -1,6 +1,7 @@ #ifndef WASM_CONCRETE_RT_HPP #define WASM_CONCRETE_RT_HPP +#include "controls.hpp" #include "wasm/profile.hpp" #include "wasm/utils.hpp" #include @@ -146,6 +147,18 @@ struct Num { return res; } + // i32.div_u (Unsigned division with traps) + inline Num i32_div_u(const Num &other) const { + uint32_t divisor = other.toUInt(); + uint32_t dividend = this->toUInt(); + if (divisor == 0) { + throw std::runtime_error("i32.div_u: Division by zero"); + } + Num res(static_cast(dividend / divisor)); + debug_print("i32.div_u", *this, other, res); + return res; + } + // i32.shl (Shift Left): *this << other (shift count masked by 31) inline Num i32_shl(const Num &other) const { uint32_t shift_amount = other.toUInt() & 0x1F; @@ -182,12 +195,247 @@ struct Num { debug_print("i32.and", *this, other, res); return res; } + + // f32 helpers: interpret low 32 bits of value as IEEE-754 float + static inline float f32_from_bits(uint32_t bits) { + union { + uint32_t i; + float f; + } u; + u.i = bits; + return u.f; + } + static inline uint32_t f32_to_bits(float f) { + union { + uint32_t i; + float f; + } u; + u.f = f; + return u.i; + } + static inline bool f32_is_nan(uint32_t bits) { + // Exponent all ones and mantissa non-zero -> NaN for IEEE-754 single + return (bits & 0x7F800000u) == 0x7F800000u && (bits & 0x007FFFFFu) != 0; + } + + // f32.add + inline Num f32_add(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + float r = a + b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.add", *this, other, res); + return res; + } + + // f32.sub + inline Num f32_sub(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + float r = a - b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.sub", *this, other, res); + return res; + } + + // f32.mul + inline Num f32_mul(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + float r = a * b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.mul", *this, other, res); + return res; + } + + // f32.div + inline Num f32_div(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + float r = a / b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.div", *this, other, res); + return res; + } + + // f32.eq : false if either is NaN + inline Num f32_eq(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) { + Num res = WasmBool(false); + debug_print("f32.eq", *this, other, res); + return res; + } + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + Num res = WasmBool(a == b); + debug_print("f32.eq", *this, other, res); + return res; + } + + // f32.ne : true if values are unordered or not equal (i.e., NaN makes it + // true) + inline Num f32_ne(const Num &other) const { + uint32_t a_bits = toUInt(); + uint32_t b_bits = other.toUInt(); + // per wasm: if either is NaN, f32.ne is true + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) { + Num res = WasmBool(true); + debug_print("f32.ne", *this, other, res); + return res; + } + float a = f32_from_bits(a_bits); + float b = f32_from_bits(b_bits); + Num res = WasmBool(a != b); + debug_print("f32.ne", *this, other, res); + return res; + } + + // ordered comparisons: return false if any operand is NaN + inline Num f32_lt(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) + return WasmBool(false); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + Num res = WasmBool(a < b); + debug_print("f32.lt", *this, other, res); + return res; + } + inline Num f32_le(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) + return WasmBool(false); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + Num res = WasmBool(a <= b); + debug_print("f32.le", *this, other, res); + return res; + } + inline Num f32_gt(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) + return WasmBool(false); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + Num res = WasmBool(a > b); + debug_print("f32.gt", *this, other, res); + return res; + } + inline Num f32_ge(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits) || f32_is_nan(b_bits)) + return WasmBool(false); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + Num res = WasmBool(a >= b); + debug_print("f32.ge", *this, other, res); + return res; + } + + // f32.abs: clear sign bit + inline Num f32_abs() const { + uint32_t a_bits = toUInt(); + uint32_t r_bits = a_bits & 0x7FFFFFFFu; + Num res(static_cast(r_bits)); + debug_print("f32.abs", *this, *this, res); + return res; + } + + // f32.neg: flip sign bit + inline Num f32_neg() const { + uint32_t a_bits = toUInt(); + uint32_t r_bits = a_bits ^ 0x80000000u; + Num res(static_cast(r_bits)); + debug_print("f32.neg", *this, *this, res); + return res; + } + + // f32.min / f32.max: follow wasm-ish semantics: if either is NaN, return NaN + // (propagate) + inline Num f32_min(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits)) + return Num(static_cast(a_bits)); + if (f32_is_nan(b_bits)) + return Num(static_cast(b_bits)); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + // If values compare equal choose one to preserve signed zero: pick the one + // whose sign bit is set for min when both zeros (so -0 wins for min). + if (a == b) { + if ((a_bits & 0x80000000u) || (b_bits & 0x80000000u)) + return Num( + static_cast((a_bits & 0x80000000u) ? a_bits : b_bits)); + return Num(static_cast(a_bits)); + } + float r = (a < b) ? a : b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.min", *this, other, res); + return res; + } + + inline Num f32_max(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + if (f32_is_nan(a_bits)) + return Num(static_cast(a_bits)); + if (f32_is_nan(b_bits)) + return Num(static_cast(b_bits)); + float a = f32_from_bits(a_bits), b = f32_from_bits(b_bits); + if (a == b) { + if ((a_bits & 0x80000000u) || (b_bits & 0x80000000u)) + return Num( + static_cast((a_bits & 0x80000000u) ? b_bits : a_bits)); + return Num(static_cast(a_bits)); + } + float r = (a > b) ? a : b; + uint32_t r_bits = f32_to_bits(r); + Num res(static_cast(r_bits)); + debug_print("f32.max", *this, other, res); + return res; + } + + // f32.copysign: result has magnitude of lhs, sign of rhs + inline Num f32_copysign(const Num &other) const { + uint32_t a_bits = toUInt(), b_bits = other.toUInt(); + uint32_t r_bits = (a_bits & 0x7FFFFFFFu) | (b_bits & 0x80000000u); + Num res(static_cast(r_bits)); + debug_print("f32.copysign", *this, other, res); + return res; + } }; static Num I32V(int v) { return v; } static Num I64V(int64_t v) { return v; } +static Num F32V(float f) { + union { + uint32_t i; + float f; + } u; + u.f = f; + return static_cast(u.i); +} + +static Num F64V(double d) { + union { + uint64_t i; + double d; + } u; + u.d = d; + return static_cast(u.i); +} + const int STACK_SIZE = 1024 * 64; class Stack_t { @@ -449,7 +697,34 @@ struct Memory_t { } }; - static Memory_t Memory(1); // 1 page memory +struct FuncTable_t { + FuncTable_t() : table(20) {} + std::vector table; + + Func_t read(int32_t index) { + if (index < 0 || index >= table.size()) { + throw std::runtime_error("Function table read out of bounds: " + + std::to_string(index)); + } + if (!table[index]) { + throw std::runtime_error("Function table entry at index " + + std::to_string(index) + " is empty or invalid"); + } + return table[index]; + } + + std::monostate set(Num offset, int32_t index, Func_t func) { + if (index < 0 || index >= table.size()) { + throw std::runtime_error("Function table set out of bounds: " + + std::to_string(index)); + } + table[offset.toInt() + index] = func; + return std::monostate{}; + } +}; + +static FuncTable_t FuncTable; + #endif // WASM_CONCRETE_RT_HPP \ No newline at end of file diff --git a/headers/wasm/controls.hpp b/headers/wasm/controls.hpp index ae0997828..dd25f78cb 100644 --- a/headers/wasm/controls.hpp +++ b/headers/wasm/controls.hpp @@ -64,4 +64,6 @@ struct Control { Control(Cont_t cont, MCont_t mcont) : cont(cont), mcont(mcont) {} }; +using Func_t = std::function; + #endif // WASM_CONTROLS_HPP \ No newline at end of file diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index fefc126be..50364ec22 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -573,6 +573,7 @@ struct NodeBox { int instr_cost; bool fillIfElseNode(SymVal cond, int id); + bool fillCallIndirectNode(SymVal cond, int id); std::monostate fillFinishedNode(); std::monostate fillFailedNode(); std::monostate fillUnreachableNode(); @@ -629,17 +630,10 @@ struct IfElseNode : Node { std::unique_ptr true_branch; std::unique_ptr false_branch; int id; - std::optional snapshot; IfElseNode(SymVal cond, NodeBox *parent, int id) : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)), id(id), - snapshot(std::nullopt) {} - - IfElseNode(SymVal cond, NodeBox *parent, int id, Snapshot_t snapshot) - : cond(cond), true_branch(std::make_unique(parent)), - false_branch(std::make_unique(parent)), id(id), - snapshot(snapshot) {} + false_branch(std::make_unique(parent)), id(id) {} std::string to_string() override { std::string result = "IfElseNode {\n"; @@ -682,6 +676,49 @@ struct IfElseNode : Node { } }; +struct CallIndirectNode : Node { + SymVal cond; + std::unordered_map> branches; + std::unique_ptr otherwise_branch; + int id; + CallIndirectNode(SymVal cond, NodeBox *parent, int id) + : cond(cond), id(id), + otherwise_branch(std::make_unique(parent)) {} + std::string to_string() override { + std::string result = "CallIndirectNode {\n"; + for (const auto &pair : branches) { + result += " branch " + std::to_string(pair.first) + ": "; + if (pair.second && pair.second->node) { + result += pair.second->node->to_string(); + } else { + result += "nullptr"; + } + result += "\n"; + } + result += "}"; + return result; + } + + void generate_dot(std::ostream &os, int parent_dot_id, + const std::string &edge_label) override { + int current_node_dot_id = current_id; + current_id += 1; + + graphviz_node(os, current_node_dot_id, "Branch", "diamond", "lightyellow"); + + // Draw edge from parent if this is not the root node + if (parent_dot_id != -1) { + graphviz_edge(os, parent_dot_id, current_node_dot_id, edge_label); + } + for (const auto &pair : branches) { + assert(pair.second != nullptr); + assert(pair.second->node != nullptr); + pair.second->node->generate_dot(os, current_node_dot_id, + "branch " + std::to_string(pair.first)); + } + } +}; + struct UnExploredNode : Node { UnExploredNode() {} std::string to_string() override { return "UnexploredNode"; } @@ -792,8 +829,7 @@ inline NodeBox::NodeBox(NodeBox *parent) inline bool NodeBox::fillIfElseNode(SymVal cond, int id) { // fill the current NodeBox with an ifelse branch node when it's unexplored if (auto ptr = dynamic_cast(node.get())) { - node = - std::make_unique(cond, this, id, ptr->move_out_snapshot()); + node = std::make_unique(cond, this, id); return true; } else if (dynamic_cast(node.get())) { node = std::make_unique(cond, this, id); @@ -810,6 +846,28 @@ inline bool NodeBox::fillIfElseNode(SymVal cond, int id) { return false; } +inline bool NodeBox::fillCallIndirectNode(SymVal cond, int id) { + // fill the current NodeBox with a call_indirect branch node when it's + // unexplored + if (auto ptr = dynamic_cast(node.get())) { + node = std::make_unique(cond, this, id); + return true; + } else if (dynamic_cast(node.get())) { + node = std::make_unique(cond, this, id); + return true; + } else if (dynamic_cast(node.get()) != nullptr) { + assert(false && + "Unexpected traversal: arrived at a node marked 'NotToExplore'."); + return false; + } + + assert( + dynamic_cast(node.get()) != nullptr && + "Current node is not an Unexplored nor a CallIndirectNode, cannot fill " + "it!"); + return false; +} + inline std::monostate NodeBox::fillSnapshotNode(Snapshot_t snapshot) { if (this->isUnexplored()) { node = std::make_unique(snapshot); @@ -839,6 +897,7 @@ inline std::monostate NodeBox::fillFailedNode() { if (this->isUnexplored()) { node = std::make_unique(); } else { + std::cout << "Fill Failed Node" << node->to_string() << std::endl; assert(dynamic_cast(node.get()) != nullptr); } return std::monostate(); @@ -869,8 +928,7 @@ inline std::vector NodeBox::collect_path_conds() { auto result = std::vector(); while (box->parent) { auto parent = box->parent; - auto if_else_node = dynamic_cast(parent->node.get()); - if (if_else_node) { + if (auto if_else_node = dynamic_cast(parent->node.get())) { if (if_else_node->true_branch.get() == box) { // If the current box is the true branch, add the condition result.push_back(if_else_node->cond); @@ -880,6 +938,33 @@ inline std::vector NodeBox::collect_path_conds() { } else { throw std::runtime_error("Unexpected node structure in explore tree"); } + } else if (auto call_indirect_node = + dynamic_cast(parent->node.get())) { + // Find which branch we are in + bool found = false; + for (const auto &pair : call_indirect_node->branches) { + if (pair.second.get() == box) { + // We are in this branch + // Add the condition that leads to this branch + result.push_back( + call_indirect_node->cond.eq(Concrete(I32V(pair.first)))); + found = true; + break; + } + } + if (!found) { + // We must be in the otherwise branch + if (call_indirect_node->otherwise_branch.get() != box) { + throw std::runtime_error("Unexpected node structure in explore tree"); + } + // Add the negated conditions for all other branches + SymVal negated_conditions = Concrete(I32V(1)); // true + for (const auto &pair : call_indirect_node->branches) { + negated_conditions = negated_conditions.bitwise_and( + call_indirect_node->cond.neq(Concrete(I32V(pair.first)))); + } + result.push_back(negated_conditions); + } } // Move to parent box = box->parent; @@ -982,6 +1067,14 @@ class ExploreTree_t { return std::monostate(); } + std::monostate fillCallIndirectNode(SymVal cond, int id) { + if (cursor->fillCallIndirectNode(cond, id)) { + auto indirect_node = dynamic_cast(cursor->node.get()); + register_new_node(indirect_node->otherwise_branch.get()); + } + return std::monostate(); + } + std::monostate fillNotToExploredNode() { return cursor->fillNotToExploreNode(); } @@ -1060,6 +1153,27 @@ class ExploreTree_t { return std::monostate(); } + std::monostate moveCursorIndirect(int branch_index) { + // Dont use snapshot reuse for untaken branches of indirect call + Profile.step(StepProfileKind::CURSOR_MOVE); + assert(cursor != nullptr); + auto branch_node = dynamic_cast(cursor->node.get()); + assert(branch_node != nullptr && + "Can't move cursor when the branch node is not initialized "); + if (branch_node->branches.find(branch_index) == + branch_node->branches.end()) { + // Create a new branch + branch_node->branches[branch_index] = std::make_unique(cursor); + register_new_node(branch_node->branches[branch_index].get()); + } + cursor = branch_node->branches[branch_index].get(); + int cost_from_parent = CostManager.dump_instr_cost(); + int cost_from_root = + cost_from_parent + (cursor->parent ? cursor->parent->instr_cost : 0); + cursor->instr_cost = cost_from_root; + return std::monostate(); + } + std::monostate print() { std::cout << root->node->to_string() << std::endl; return std::monostate(); @@ -1108,6 +1222,12 @@ class ExploreTree_t { result.unexplored_count += 1; } else if (dynamic_cast(node->node.get())) { result.not_to_explore_count += 1; + } else if (auto call_indirect_node = + dynamic_cast(node->node.get())) { + for (const auto &pair : call_indirect_node->branches) { + dfs(pair.second.get()); + } + dfs(call_indirect_node->otherwise_branch.get()); } else { throw std::runtime_error("Unknown node type in explore tree"); } @@ -1491,8 +1611,8 @@ Snapshot_t::resume_execution_by_model(NodeBox *node, z3::model &model) const { return cont(mcont); } -[[deprecated]] -inline std::monostate Snapshot_t::resume_execution(NodeBox *node) const { +[[deprecated]] inline std::monostate +Snapshot_t::resume_execution(NodeBox *node) const { // Reset explore tree's cursor and restore symbolic states ExploreTree.set_cursor(node); restore_states_to_global(); diff --git a/src/main/java/wasm/WatParser.java b/src/main/java/wasm/WatParser.java index 3895179d5..b364ddea6 100644 --- a/src/main/java/wasm/WatParser.java +++ b/src/main/java/wasm/WatParser.java @@ -1648,7 +1648,6 @@ public final PlainInstrContext plainInstr() throws RecognitionException { enterRule(_localctx, 40, RULE_plainInstr); int _la; try { - int _alt; setState(357); _errHandler.sync(this); switch ( getInterpreter().adaptivePredict(_input,18,_ctx) ) { @@ -1705,24 +1704,18 @@ public final PlainInstrContext plainInstr() throws RecognitionException { match(BR_TABLE); setState(289); _errHandler.sync(this); - _alt = 1; + _la = _input.LA(1); do { - switch (_alt) { - case 1: - { - { - setState(288); - idx(); - } - } - break; - default: - throw new NoViableAltException(this); + { + { + setState(288); + idx(); + } } setState(291); _errHandler.sync(this); - _alt = getInterpreter().adaptivePredict(_input,13,_ctx); - } while ( _alt!=2 && _alt!=org.antlr.v4.runtime.atn.ATN.INVALID_ALT_NUMBER ); + _la = _input.LA(1); + } while ( _la==NAT || _la==VAR ); } break; case 8: @@ -2941,14 +2934,14 @@ public final BlockInstrContext blockInstr() throws RecognitionException { match(END); setState(473); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,34,_ctx) ) { - case 1: + _la = _input.LA(1); + if (_la==VAR) { { setState(472); bindVar(); } - break; } + } break; case LOOP: @@ -2972,14 +2965,14 @@ public final BlockInstrContext blockInstr() throws RecognitionException { match(END); setState(482); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,36,_ctx) ) { - case 1: + _la = _input.LA(1); + if (_la==VAR) { { setState(481); bindVar(); } - break; } + } break; case IF: @@ -3025,14 +3018,14 @@ public final BlockInstrContext blockInstr() throws RecognitionException { match(END); setState(498); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,40,_ctx) ) { - case 1: + _la = _input.LA(1); + if (_la==VAR) { { setState(497); bindVar(); } - break; } + } break; case TRY: @@ -3379,14 +3372,14 @@ public final ExprContext expr() throws RecognitionException { match(BLOCK); setState(541); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,45,_ctx) ) { - case 1: + _la = _input.LA(1); + if (_la==VAR) { { setState(540); bindVar(); } - break; } + setState(543); block(); } @@ -3398,14 +3391,14 @@ public final ExprContext expr() throws RecognitionException { match(LOOP); setState(546); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,46,_ctx) ) { - case 1: + _la = _input.LA(1); + if (_la==VAR) { { setState(545); bindVar(); } - break; } + setState(548); block(); } @@ -4351,17 +4344,13 @@ public InstrContext instr() { public TerminalNode RPAR(int i) { return getToken(WatParser.RPAR, i); } + public TerminalNode FUNC() { return getToken(WatParser.FUNC, 0); } public List idx() { return getRuleContexts(IdxContext.class); } public IdxContext idx(int i) { return getRuleContext(IdxContext.class,i); } - public OffsetContext offset() { - return getRuleContext(OffsetContext.class,0); - } - public TerminalNode DECLARE() { return getToken(WatParser.DECLARE, 0); } - public TerminalNode FUNC() { return getToken(WatParser.FUNC, 0); } public ElemContext(ParserRuleContext parent, int invokingState) { super(parent, invokingState); } @@ -4386,126 +4375,36 @@ public final ElemContext elem() throws RecognitionException { enterRule(_localctx, 94, RULE_elem); int _la; try { - setState(723); + enterOuterAlt(_localctx, 1); + { + setState(679); + match(LPAR); + setState(680); + match(ELEM); + setState(681); + match(LPAR); + setState(682); + instr(); + setState(683); + match(RPAR); + setState(684); + match(FUNC); + setState(688); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,73,_ctx) ) { - case 1: - enterOuterAlt(_localctx, 1); + _la = _input.LA(1); + while (_la==NAT || _la==VAR) { { - setState(679); - match(LPAR); - setState(680); - match(ELEM); - setState(682); - _errHandler.sync(this); - _la = _input.LA(1); - if (_la==NAT || _la==VAR) { - { - setState(681); - idx(); - } - } - - setState(684); - match(LPAR); - setState(685); - instr(); - setState(686); - match(RPAR); - setState(690); - _errHandler.sync(this); - _la = _input.LA(1); - while (_la==NAT || _la==VAR) { - { - { - setState(687); - idx(); - } - } - setState(692); - _errHandler.sync(this); - _la = _input.LA(1); - } - setState(693); - match(RPAR); - } - break; - case 2: - enterOuterAlt(_localctx, 2); { - setState(695); - match(LPAR); - setState(696); - match(ELEM); - setState(698); - _errHandler.sync(this); - _la = _input.LA(1); - if (_la==NAT || _la==VAR) { - { - setState(697); - idx(); - } - } - - setState(700); - offset(); - setState(704); - _errHandler.sync(this); - _la = _input.LA(1); - while (_la==NAT || _la==VAR) { - { - { - setState(701); - idx(); - } - } - setState(706); - _errHandler.sync(this); - _la = _input.LA(1); + setState(685); + idx(); } - setState(707); - match(RPAR); } - break; - case 3: - enterOuterAlt(_localctx, 3); - { - setState(709); - match(LPAR); - setState(710); - match(ELEM); - setState(712); - _errHandler.sync(this); - _la = _input.LA(1); - if (_la==NAT || _la==VAR) { - { - setState(711); - idx(); - } - } - - setState(714); - match(DECLARE); - setState(715); - match(FUNC); - setState(719); + setState(690); _errHandler.sync(this); _la = _input.LA(1); - while (_la==NAT || _la==VAR) { - { - { - setState(716); - idx(); - } - } - setState(721); - _errHandler.sync(this); - _la = _input.LA(1); - } - setState(722); - match(RPAR); - } - break; + } + setState(691); + match(RPAR); } } catch (RecognitionException re) { @@ -4556,23 +4455,23 @@ public final TableContext table() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(725); + setState(693); match(LPAR); - setState(726); + setState(694); match(TABLE); - setState(728); + setState(696); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(727); + setState(695); bindVar(); } } - setState(730); + setState(698); tableField(); - setState(731); + setState(699); match(RPAR); } } @@ -4637,58 +4536,58 @@ public final TableFieldContext tableField() throws RecognitionException { enterRule(_localctx, 98, RULE_tableField); int _la; try { - setState(751); + setState(719); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,76,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,70,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(733); + setState(701); tableType(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(734); + setState(702); inlineImport(); - setState(735); + setState(703); tableType(); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(737); + setState(705); inlineExport(); - setState(738); + setState(706); tableField(); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(740); + setState(708); refType(); - setState(741); + setState(709); match(LPAR); - setState(742); + setState(710); match(ELEM); - setState(746); + setState(714); _errHandler.sync(this); _la = _input.LA(1); while (_la==NAT || _la==VAR) { { { - setState(743); + setState(711); idx(); } } - setState(748); + setState(716); _errHandler.sync(this); _la = _input.LA(1); } - setState(749); + setState(717); match(RPAR); } break; @@ -4753,84 +4652,84 @@ public final DataContext data() throws RecognitionException { enterRule(_localctx, 100, RULE_data); int _la; try { - setState(783); + setState(751); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,81,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,75,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(753); + setState(721); match(LPAR); - setState(754); + setState(722); match(DATA); - setState(756); + setState(724); _errHandler.sync(this); _la = _input.LA(1); if (_la==NAT || _la==VAR) { { - setState(755); + setState(723); idx(); } } - setState(758); + setState(726); match(LPAR); - setState(759); + setState(727); instr(); - setState(760); + setState(728); match(RPAR); - setState(764); + setState(732); _errHandler.sync(this); _la = _input.LA(1); while (_la==STRING_) { { { - setState(761); + setState(729); match(STRING_); } } - setState(766); + setState(734); _errHandler.sync(this); _la = _input.LA(1); } - setState(767); + setState(735); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(769); + setState(737); match(LPAR); - setState(770); + setState(738); match(DATA); - setState(772); + setState(740); _errHandler.sync(this); _la = _input.LA(1); if (_la==NAT || _la==VAR) { { - setState(771); + setState(739); idx(); } } - setState(774); + setState(742); offset(); - setState(778); + setState(746); _errHandler.sync(this); _la = _input.LA(1); while (_la==STRING_) { { { - setState(775); + setState(743); match(STRING_); } } - setState(780); + setState(748); _errHandler.sync(this); _la = _input.LA(1); } - setState(781); + setState(749); match(RPAR); } break; @@ -4884,23 +4783,23 @@ public final MemoryContext memory() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(785); + setState(753); match(LPAR); - setState(786); + setState(754); match(MEMORY); - setState(788); + setState(756); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(787); + setState(755); bindVar(); } } - setState(790); + setState(758); memoryField(); - setState(791); + setState(759); match(RPAR); } } @@ -4960,56 +4859,56 @@ public final MemoryFieldContext memoryField() throws RecognitionException { enterRule(_localctx, 104, RULE_memoryField); int _la; try { - setState(809); + setState(777); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,84,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,78,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(793); + setState(761); memoryType(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(794); + setState(762); inlineImport(); - setState(795); + setState(763); memoryType(); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(797); + setState(765); inlineExport(); - setState(798); + setState(766); memoryField(); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(800); + setState(768); match(LPAR); - setState(801); + setState(769); match(DATA); - setState(805); + setState(773); _errHandler.sync(this); _la = _input.LA(1); while (_la==STRING_) { { { - setState(802); + setState(770); match(STRING_); } } - setState(807); + setState(775); _errHandler.sync(this); _la = _input.LA(1); } - setState(808); + setState(776); match(RPAR); } break; @@ -5063,23 +4962,23 @@ public final GlobalContext global() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(811); + setState(779); match(LPAR); - setState(812); + setState(780); match(GLOBAL); - setState(814); + setState(782); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(813); + setState(781); bindVar(); } } - setState(816); + setState(784); globalField(); - setState(817); + setState(785); match(RPAR); } } @@ -5134,33 +5033,33 @@ public final GlobalFieldContext globalField() throws RecognitionException { GlobalFieldContext _localctx = new GlobalFieldContext(_ctx, getState()); enterRule(_localctx, 108, RULE_globalField); try { - setState(828); + setState(796); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,86,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,80,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(819); + setState(787); globalType(); - setState(820); + setState(788); constExpr(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(822); + setState(790); inlineImport(); - setState(823); + setState(791); globalType(); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(825); + setState(793); inlineExport(); - setState(826); + setState(794); globalField(); } break; @@ -5227,121 +5126,121 @@ public final ImportDescContext importDesc() throws RecognitionException { enterRule(_localctx, 110, RULE_importDesc); int _la; try { - setState(870); + setState(838); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,92,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,86,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(830); + setState(798); match(LPAR); - setState(831); + setState(799); match(FUNC); - setState(833); + setState(801); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(832); + setState(800); bindVar(); } } - setState(835); + setState(803); typeUse(); - setState(836); + setState(804); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(838); + setState(806); match(LPAR); - setState(839); + setState(807); match(FUNC); - setState(841); + setState(809); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(840); + setState(808); bindVar(); } } - setState(843); + setState(811); funcType(); - setState(844); + setState(812); match(RPAR); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(846); + setState(814); match(LPAR); - setState(847); + setState(815); match(TABLE); - setState(849); + setState(817); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(848); + setState(816); bindVar(); } } - setState(851); + setState(819); tableType(); - setState(852); + setState(820); match(RPAR); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(854); + setState(822); match(LPAR); - setState(855); + setState(823); match(MEMORY); - setState(857); + setState(825); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(856); + setState(824); bindVar(); } } - setState(859); + setState(827); memoryType(); - setState(860); + setState(828); match(RPAR); } break; case 5: enterOuterAlt(_localctx, 5); { - setState(862); + setState(830); match(LPAR); - setState(863); + setState(831); match(GLOBAL); - setState(865); + setState(833); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(864); + setState(832); bindVar(); } } - setState(867); + setState(835); globalType(); - setState(868); + setState(836); match(RPAR); } break; @@ -5397,17 +5296,17 @@ public final SimportContext simport() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(872); + setState(840); match(LPAR); - setState(873); + setState(841); match(IMPORT); - setState(874); + setState(842); name(); - setState(875); + setState(843); name(); - setState(876); + setState(844); importDesc(); - setState(877); + setState(845); match(RPAR); } } @@ -5458,15 +5357,15 @@ public final InlineImportContext inlineImport() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(879); + setState(847); match(LPAR); - setState(880); + setState(848); match(IMPORT); - setState(881); + setState(849); name(); - setState(882); + setState(850); name(); - setState(883); + setState(851); match(RPAR); } } @@ -5515,58 +5414,58 @@ public final ExportDescContext exportDesc() throws RecognitionException { ExportDescContext _localctx = new ExportDescContext(_ctx, getState()); enterRule(_localctx, 116, RULE_exportDesc); try { - setState(905); + setState(873); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,93,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,87,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(885); + setState(853); match(LPAR); - setState(886); + setState(854); match(FUNC); - setState(887); + setState(855); idx(); - setState(888); + setState(856); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(890); + setState(858); match(LPAR); - setState(891); + setState(859); match(TABLE); - setState(892); + setState(860); idx(); - setState(893); + setState(861); match(RPAR); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(895); + setState(863); match(LPAR); - setState(896); + setState(864); match(MEMORY); - setState(897); + setState(865); idx(); - setState(898); + setState(866); match(RPAR); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(900); + setState(868); match(LPAR); - setState(901); + setState(869); match(GLOBAL); - setState(902); + setState(870); idx(); - setState(903); + setState(871); match(RPAR); } break; @@ -5619,15 +5518,15 @@ public final Export_Context export_() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(907); + setState(875); match(LPAR); - setState(908); + setState(876); match(EXPORT); - setState(909); + setState(877); name(); - setState(910); + setState(878); exportDesc(); - setState(911); + setState(879); match(RPAR); } } @@ -5675,13 +5574,13 @@ public final InlineExportContext inlineExport() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(913); + setState(881); match(LPAR); - setState(914); + setState(882); match(EXPORT); - setState(915); + setState(883); name(); - setState(916); + setState(884); match(RPAR); } } @@ -5736,25 +5635,25 @@ public final TagContext tag() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(918); + setState(886); match(LPAR); - setState(919); + setState(887); match(TAG); - setState(921); + setState(889); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(920); + setState(888); bindVar(); } } - setState(923); + setState(891); typeUse(); - setState(924); + setState(892); funcType(); - setState(925); + setState(893); match(RPAR); } } @@ -5806,23 +5705,23 @@ public final TypeDefContext typeDef() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(927); + setState(895); match(LPAR); - setState(928); + setState(896); match(TYPE); - setState(930); + setState(898); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(929); + setState(897); bindVar(); } } - setState(932); + setState(900); defType(); - setState(933); + setState(901); match(RPAR); } } @@ -5870,13 +5769,13 @@ public final Start_Context start_() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(935); + setState(903); match(LPAR); - setState(936); + setState(904); match(START_); - setState(937); + setState(905); idx(); - setState(938); + setState(906); match(RPAR); } } @@ -5949,83 +5848,83 @@ public final ModuleFieldContext moduleField() throws RecognitionException { ModuleFieldContext _localctx = new ModuleFieldContext(_ctx, getState()); enterRule(_localctx, 128, RULE_moduleField); try { - setState(951); + setState(919); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,96,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,90,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(940); + setState(908); typeDef(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(941); + setState(909); global(); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(942); + setState(910); table(); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(943); + setState(911); memory(); } break; case 5: enterOuterAlt(_localctx, 5); { - setState(944); + setState(912); function(); } break; case 6: enterOuterAlt(_localctx, 6); { - setState(945); + setState(913); elem(); } break; case 7: enterOuterAlt(_localctx, 7); { - setState(946); + setState(914); data(); } break; case 8: enterOuterAlt(_localctx, 8); { - setState(947); + setState(915); start_(); } break; case 9: enterOuterAlt(_localctx, 9); { - setState(948); + setState(916); simport(); } break; case 10: enterOuterAlt(_localctx, 10); { - setState(949); + setState(917); export_(); } break; case 11: enterOuterAlt(_localctx, 11); { - setState(950); + setState(918); tag(); } break; @@ -6080,35 +5979,35 @@ public final Module_Context module_() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(953); + setState(921); match(LPAR); - setState(954); + setState(922); match(MODULE); - setState(956); + setState(924); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(955); + setState(923); match(VAR); } } - setState(961); + setState(929); _errHandler.sync(this); _la = _input.LA(1); while (_la==LPAR) { { { - setState(958); + setState(926); moduleField(); } } - setState(963); + setState(931); _errHandler.sync(this); _la = _input.LA(1); } - setState(964); + setState(932); match(RPAR); } } @@ -6163,34 +6062,34 @@ public final ScriptModuleContext scriptModule() throws RecognitionException { enterRule(_localctx, 132, RULE_scriptModule); int _la; try { - setState(994); + setState(962); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,103,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,97,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(966); + setState(934); module_(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(967); + setState(935); match(LPAR); - setState(968); + setState(936); match(MODULE); - setState(970); + setState(938); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(969); + setState(937); match(VAR); } } - setState(972); + setState(940); _la = _input.LA(1); if ( !(_la==BIN || _la==QUOTE) ) { _errHandler.recoverInline(this); @@ -6200,60 +6099,60 @@ public final ScriptModuleContext scriptModule() throws RecognitionException { _errHandler.reportMatch(this); consume(); } - setState(976); + setState(944); _errHandler.sync(this); _la = _input.LA(1); while (_la==STRING_) { { { - setState(973); + setState(941); match(STRING_); } } - setState(978); + setState(946); _errHandler.sync(this); _la = _input.LA(1); } - setState(979); + setState(947); match(RPAR); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(980); + setState(948); match(LPAR); - setState(981); + setState(949); match(MODULE); - setState(982); + setState(950); match(DEFINITION); - setState(984); + setState(952); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(983); + setState(951); match(VAR); } } - setState(986); + setState(954); match(BIN); - setState(990); + setState(958); _errHandler.sync(this); _la = _input.LA(1); while (_la==STRING_) { { { - setState(987); + setState(955); match(STRING_); } } - setState(992); + setState(960); _errHandler.sync(this); _la = _input.LA(1); } - setState(993); + setState(961); match(RPAR); } break; @@ -6307,54 +6206,54 @@ public final Action_Context action_() throws RecognitionException { enterRule(_localctx, 134, RULE_action_); int _la; try { - setState(1013); + setState(981); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,106,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,100,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(996); + setState(964); match(LPAR); - setState(997); + setState(965); match(INVOKE); - setState(999); + setState(967); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(998); + setState(966); match(VAR); } } - setState(1001); + setState(969); name(); - setState(1002); + setState(970); constList(); - setState(1003); + setState(971); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1005); + setState(973); match(LPAR); - setState(1006); + setState(974); match(GET); - setState(1008); + setState(976); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1007); + setState(975); match(VAR); } } - setState(1010); + setState(978); name(); - setState(1011); + setState(979); match(RPAR); } break; @@ -6416,137 +6315,137 @@ public final AssertionContext assertion() throws RecognitionException { AssertionContext _localctx = new AssertionContext(_ctx, getState()); enterRule(_localctx, 136, RULE_assertion); try { - setState(1067); + setState(1035); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,107,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,101,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(1015); + setState(983); match(LPAR); - setState(1016); + setState(984); match(ASSERT_MALFORMED); - setState(1017); + setState(985); scriptModule(); - setState(1018); + setState(986); match(STRING_); - setState(1019); + setState(987); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1021); + setState(989); match(LPAR); - setState(1022); + setState(990); match(ASSERT_INVALID); - setState(1023); + setState(991); scriptModule(); - setState(1024); + setState(992); match(STRING_); - setState(1025); + setState(993); match(RPAR); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(1027); + setState(995); match(LPAR); - setState(1028); + setState(996); match(ASSERT_UNLINKABLE); - setState(1029); + setState(997); scriptModule(); - setState(1030); + setState(998); match(STRING_); - setState(1031); + setState(999); match(RPAR); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(1033); + setState(1001); match(LPAR); - setState(1034); + setState(1002); match(ASSERT_TRAP); - setState(1035); + setState(1003); scriptModule(); - setState(1036); + setState(1004); match(STRING_); - setState(1037); + setState(1005); match(RPAR); } break; case 5: enterOuterAlt(_localctx, 5); { - setState(1039); + setState(1007); match(LPAR); - setState(1040); + setState(1008); match(ASSERT_RETURN); - setState(1041); + setState(1009); action_(); - setState(1042); + setState(1010); constList(); - setState(1043); + setState(1011); match(RPAR); } break; case 6: enterOuterAlt(_localctx, 6); { - setState(1045); + setState(1013); match(LPAR); - setState(1046); + setState(1014); match(ASSERT_RETURN_CANONICAL_NAN); - setState(1047); + setState(1015); action_(); - setState(1048); + setState(1016); match(RPAR); } break; case 7: enterOuterAlt(_localctx, 7); { - setState(1050); + setState(1018); match(LPAR); - setState(1051); + setState(1019); match(ASSERT_RETURN_ARITHMETIC_NAN); - setState(1052); + setState(1020); action_(); - setState(1053); + setState(1021); match(RPAR); } break; case 8: enterOuterAlt(_localctx, 8); { - setState(1055); + setState(1023); match(LPAR); - setState(1056); + setState(1024); match(ASSERT_TRAP); - setState(1057); + setState(1025); action_(); - setState(1058); + setState(1026); match(STRING_); - setState(1059); + setState(1027); match(RPAR); } break; case 9: enterOuterAlt(_localctx, 9); { - setState(1061); + setState(1029); match(LPAR); - setState(1062); + setState(1030); match(ASSERT_EXHAUSTION); - setState(1063); + setState(1031); action_(); - setState(1064); + setState(1032); match(STRING_); - setState(1065); + setState(1033); match(RPAR); } break; @@ -6611,64 +6510,64 @@ public final CmdContext cmd() throws RecognitionException { enterRule(_localctx, 138, RULE_cmd); int _la; try { - setState(1082); + setState(1050); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,109,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,103,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(1069); + setState(1037); action_(); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1070); + setState(1038); assertion(); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(1071); + setState(1039); scriptModule(); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(1072); + setState(1040); match(LPAR); - setState(1073); + setState(1041); match(REGISTER); - setState(1074); + setState(1042); name(); - setState(1076); + setState(1044); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1075); + setState(1043); match(VAR); } } - setState(1078); + setState(1046); match(RPAR); } break; case 5: enterOuterAlt(_localctx, 5); { - setState(1080); + setState(1048); meta(); } break; case 6: enterOuterAlt(_localctx, 6); { - setState(1081); + setState(1049); instance(); } break; @@ -6721,33 +6620,33 @@ public final InstanceContext instance() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(1084); + setState(1052); match(LPAR); - setState(1085); + setState(1053); match(MODULE); - setState(1086); + setState(1054); match(INSTANCE); - setState(1088); + setState(1056); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,110,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,104,_ctx) ) { case 1: { - setState(1087); + setState(1055); match(VAR); } break; } - setState(1091); + setState(1059); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1090); + setState(1058); match(VAR); } } - setState(1093); + setState(1061); match(RPAR); } } @@ -6801,108 +6700,108 @@ public final MetaContext meta() throws RecognitionException { enterRule(_localctx, 142, RULE_meta); int _la; try { - setState(1127); + setState(1095); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,117,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,111,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(1095); + setState(1063); match(LPAR); - setState(1096); + setState(1064); match(SCRIPT); - setState(1098); + setState(1066); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1097); + setState(1065); match(VAR); } } - setState(1103); + setState(1071); _errHandler.sync(this); _la = _input.LA(1); while (_la==LPAR) { { { - setState(1100); + setState(1068); cmd(); } } - setState(1105); + setState(1073); _errHandler.sync(this); _la = _input.LA(1); } - setState(1106); + setState(1074); match(RPAR); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1107); + setState(1075); match(LPAR); - setState(1108); + setState(1076); match(INPUT); - setState(1110); + setState(1078); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1109); + setState(1077); match(VAR); } } - setState(1112); + setState(1080); match(STRING_); - setState(1113); + setState(1081); match(RPAR); } break; case 3: enterOuterAlt(_localctx, 3); { - setState(1114); + setState(1082); match(LPAR); - setState(1115); + setState(1083); match(OUTPUT); - setState(1117); + setState(1085); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1116); + setState(1084); match(VAR); } } - setState(1119); + setState(1087); match(STRING_); - setState(1120); + setState(1088); match(RPAR); } break; case 4: enterOuterAlt(_localctx, 4); { - setState(1121); + setState(1089); match(LPAR); - setState(1122); + setState(1090); match(OUTPUT); - setState(1124); + setState(1092); _errHandler.sync(this); _la = _input.LA(1); if (_la==VAR) { { - setState(1123); + setState(1091); match(VAR); } } - setState(1126); + setState(1094); match(RPAR); } break; @@ -6952,13 +6851,13 @@ public final WconstContext wconst() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(1129); + setState(1097); match(LPAR); - setState(1130); + setState(1098); match(CONST); - setState(1131); + setState(1099); literal(); - setState(1132); + setState(1100); match(RPAR); } } @@ -7007,17 +6906,17 @@ public final ConstListContext constList() throws RecognitionException { try { enterOuterAlt(_localctx, 1); { - setState(1137); + setState(1105); _errHandler.sync(this); _la = _input.LA(1); while (_la==LPAR) { { { - setState(1134); + setState(1102); wconst(); } } - setState(1139); + setState(1107); _errHandler.sync(this); _la = _input.LA(1); } @@ -7073,48 +6972,48 @@ public final ScriptContext script() throws RecognitionException { enterRule(_localctx, 148, RULE_script); int _la; try { - setState(1154); + setState(1122); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,121,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,115,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(1143); + setState(1111); _errHandler.sync(this); _la = _input.LA(1); while (_la==LPAR) { { { - setState(1140); + setState(1108); cmd(); } } - setState(1145); + setState(1113); _errHandler.sync(this); _la = _input.LA(1); } - setState(1146); + setState(1114); match(EOF); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1148); + setState(1116); _errHandler.sync(this); _la = _input.LA(1); do { { { - setState(1147); + setState(1115); moduleField(); } } - setState(1150); + setState(1118); _errHandler.sync(this); _la = _input.LA(1); } while ( _la==LPAR ); - setState(1152); + setState(1120); match(EOF); } break; @@ -7167,36 +7066,36 @@ public final ModuleContext module() throws RecognitionException { enterRule(_localctx, 150, RULE_module); int _la; try { - setState(1166); + setState(1134); _errHandler.sync(this); - switch ( getInterpreter().adaptivePredict(_input,123,_ctx) ) { + switch ( getInterpreter().adaptivePredict(_input,117,_ctx) ) { case 1: enterOuterAlt(_localctx, 1); { - setState(1156); + setState(1124); module_(); - setState(1157); + setState(1125); match(EOF); } break; case 2: enterOuterAlt(_localctx, 2); { - setState(1162); + setState(1130); _errHandler.sync(this); _la = _input.LA(1); while (_la==LPAR) { { { - setState(1159); + setState(1127); moduleField(); } } - setState(1164); + setState(1132); _errHandler.sync(this); _la = _input.LA(1); } - setState(1165); + setState(1133); match(EOF); } break; @@ -7214,7 +7113,7 @@ public final ModuleContext module() throws RecognitionException { } public static final String _serializedATN = - "\u0004\u0001\u00ab\u0491\u0002\u0000\u0007\u0000\u0002\u0001\u0007\u0001"+ + "\u0004\u0001\u00ab\u0471\u0002\u0000\u0007\u0000\u0002\u0001\u0007\u0001"+ "\u0002\u0002\u0007\u0002\u0002\u0003\u0007\u0003\u0002\u0004\u0007\u0004"+ "\u0002\u0005\u0007\u0005\u0002\u0006\u0007\u0006\u0002\u0007\u0007\u0007"+ "\u0002\b\u0007\b\u0002\t\u0007\t\u0002\n\u0007\n\u0002\u000b\u0007\u000b"+ @@ -7303,165 +7202,162 @@ public final ModuleContext module() throws RecognitionException { "+\u0001+\u0001+\u0003+\u0286\b+\u0001,\u0001,\u0001,\u0001-\u0001-\u0001"+ "-\u0005-\u028e\b-\n-\f-\u0291\t-\u0001-\u0001-\u0001-\u0003-\u0296\b-"+ "\u0001-\u0005-\u0299\b-\n-\f-\u029c\t-\u0001-\u0001-\u0001.\u0001.\u0001"+ - ".\u0001.\u0001.\u0001.\u0003.\u02a6\b.\u0001/\u0001/\u0001/\u0003/\u02ab"+ - "\b/\u0001/\u0001/\u0001/\u0001/\u0005/\u02b1\b/\n/\f/\u02b4\t/\u0001/"+ - "\u0001/\u0001/\u0001/\u0001/\u0003/\u02bb\b/\u0001/\u0001/\u0005/\u02bf"+ - "\b/\n/\f/\u02c2\t/\u0001/\u0001/\u0001/\u0001/\u0001/\u0003/\u02c9\b/"+ - "\u0001/\u0001/\u0001/\u0005/\u02ce\b/\n/\f/\u02d1\t/\u0001/\u0003/\u02d4"+ - "\b/\u00010\u00010\u00010\u00030\u02d9\b0\u00010\u00010\u00010\u00011\u0001"+ - "1\u00011\u00011\u00011\u00011\u00011\u00011\u00011\u00011\u00011\u0005"+ - "1\u02e9\b1\n1\f1\u02ec\t1\u00011\u00011\u00031\u02f0\b1\u00012\u00012"+ - "\u00012\u00032\u02f5\b2\u00012\u00012\u00012\u00012\u00052\u02fb\b2\n"+ - "2\f2\u02fe\t2\u00012\u00012\u00012\u00012\u00012\u00032\u0305\b2\u0001"+ - "2\u00012\u00052\u0309\b2\n2\f2\u030c\t2\u00012\u00012\u00032\u0310\b2"+ - "\u00013\u00013\u00013\u00033\u0315\b3\u00013\u00013\u00013\u00014\u0001"+ - "4\u00014\u00014\u00014\u00014\u00014\u00014\u00014\u00014\u00054\u0324"+ - "\b4\n4\f4\u0327\t4\u00014\u00034\u032a\b4\u00015\u00015\u00015\u00035"+ - "\u032f\b5\u00015\u00015\u00015\u00016\u00016\u00016\u00016\u00016\u0001"+ - "6\u00016\u00016\u00016\u00036\u033d\b6\u00017\u00017\u00017\u00037\u0342"+ - "\b7\u00017\u00017\u00017\u00017\u00017\u00017\u00037\u034a\b7\u00017\u0001"+ - "7\u00017\u00017\u00017\u00017\u00037\u0352\b7\u00017\u00017\u00017\u0001"+ - "7\u00017\u00017\u00037\u035a\b7\u00017\u00017\u00017\u00017\u00017\u0001"+ - "7\u00037\u0362\b7\u00017\u00017\u00017\u00037\u0367\b7\u00018\u00018\u0001"+ - "8\u00018\u00018\u00018\u00018\u00019\u00019\u00019\u00019\u00019\u0001"+ - "9\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001"+ + ".\u0001.\u0001.\u0001.\u0003.\u02a6\b.\u0001/\u0001/\u0001/\u0001/\u0001"+ + "/\u0001/\u0001/\u0005/\u02af\b/\n/\f/\u02b2\t/\u0001/\u0001/\u00010\u0001"+ + "0\u00010\u00030\u02b9\b0\u00010\u00010\u00010\u00011\u00011\u00011\u0001"+ + "1\u00011\u00011\u00011\u00011\u00011\u00011\u00011\u00051\u02c9\b1\n1"+ + "\f1\u02cc\t1\u00011\u00011\u00031\u02d0\b1\u00012\u00012\u00012\u0003"+ + "2\u02d5\b2\u00012\u00012\u00012\u00012\u00052\u02db\b2\n2\f2\u02de\t2"+ + "\u00012\u00012\u00012\u00012\u00012\u00032\u02e5\b2\u00012\u00012\u0005"+ + "2\u02e9\b2\n2\f2\u02ec\t2\u00012\u00012\u00032\u02f0\b2\u00013\u00013"+ + "\u00013\u00033\u02f5\b3\u00013\u00013\u00013\u00014\u00014\u00014\u0001"+ + "4\u00014\u00014\u00014\u00014\u00014\u00014\u00054\u0304\b4\n4\f4\u0307"+ + "\t4\u00014\u00034\u030a\b4\u00015\u00015\u00015\u00035\u030f\b5\u0001"+ + "5\u00015\u00015\u00016\u00016\u00016\u00016\u00016\u00016\u00016\u0001"+ + "6\u00016\u00036\u031d\b6\u00017\u00017\u00017\u00037\u0322\b7\u00017\u0001"+ + "7\u00017\u00017\u00017\u00017\u00037\u032a\b7\u00017\u00017\u00017\u0001"+ + "7\u00017\u00017\u00037\u0332\b7\u00017\u00017\u00017\u00017\u00017\u0001"+ + "7\u00037\u033a\b7\u00017\u00017\u00017\u00017\u00017\u00017\u00037\u0342"+ + "\b7\u00017\u00017\u00017\u00037\u0347\b7\u00018\u00018\u00018\u00018\u0001"+ + "8\u00018\u00018\u00019\u00019\u00019\u00019\u00019\u00019\u0001:\u0001"+ ":\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001"+ - ":\u0003:\u038a\b:\u0001;\u0001;\u0001;\u0001;\u0001;\u0001;\u0001<\u0001"+ - "<\u0001<\u0001<\u0001<\u0001=\u0001=\u0001=\u0003=\u039a\b=\u0001=\u0001"+ - "=\u0001=\u0001=\u0001>\u0001>\u0001>\u0003>\u03a3\b>\u0001>\u0001>\u0001"+ - ">\u0001?\u0001?\u0001?\u0001?\u0001?\u0001@\u0001@\u0001@\u0001@\u0001"+ - "@\u0001@\u0001@\u0001@\u0001@\u0001@\u0001@\u0003@\u03b8\b@\u0001A\u0001"+ - "A\u0001A\u0003A\u03bd\bA\u0001A\u0005A\u03c0\bA\nA\fA\u03c3\tA\u0001A"+ - "\u0001A\u0001B\u0001B\u0001B\u0001B\u0003B\u03cb\bB\u0001B\u0001B\u0005"+ - "B\u03cf\bB\nB\fB\u03d2\tB\u0001B\u0001B\u0001B\u0001B\u0001B\u0003B\u03d9"+ - "\bB\u0001B\u0001B\u0005B\u03dd\bB\nB\fB\u03e0\tB\u0001B\u0003B\u03e3\b"+ - "B\u0001C\u0001C\u0001C\u0003C\u03e8\bC\u0001C\u0001C\u0001C\u0001C\u0001"+ - "C\u0001C\u0001C\u0003C\u03f1\bC\u0001C\u0001C\u0001C\u0003C\u03f6\bC\u0001"+ + ":\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0001:\u0003:\u036a"+ + "\b:\u0001;\u0001;\u0001;\u0001;\u0001;\u0001;\u0001<\u0001<\u0001<\u0001"+ + "<\u0001<\u0001=\u0001=\u0001=\u0003=\u037a\b=\u0001=\u0001=\u0001=\u0001"+ + "=\u0001>\u0001>\u0001>\u0003>\u0383\b>\u0001>\u0001>\u0001>\u0001?\u0001"+ + "?\u0001?\u0001?\u0001?\u0001@\u0001@\u0001@\u0001@\u0001@\u0001@\u0001"+ + "@\u0001@\u0001@\u0001@\u0001@\u0003@\u0398\b@\u0001A\u0001A\u0001A\u0003"+ + "A\u039d\bA\u0001A\u0005A\u03a0\bA\nA\fA\u03a3\tA\u0001A\u0001A\u0001B"+ + "\u0001B\u0001B\u0001B\u0003B\u03ab\bB\u0001B\u0001B\u0005B\u03af\bB\n"+ + "B\fB\u03b2\tB\u0001B\u0001B\u0001B\u0001B\u0001B\u0003B\u03b9\bB\u0001"+ + "B\u0001B\u0005B\u03bd\bB\nB\fB\u03c0\tB\u0001B\u0003B\u03c3\bB\u0001C"+ + "\u0001C\u0001C\u0003C\u03c8\bC\u0001C\u0001C\u0001C\u0001C\u0001C\u0001"+ + "C\u0001C\u0003C\u03d1\bC\u0001C\u0001C\u0001C\u0003C\u03d6\bC\u0001D\u0001"+ "D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001"+ "D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001"+ "D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001"+ "D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001"+ "D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001D\u0001"+ - "D\u0001D\u0003D\u042c\bD\u0001E\u0001E\u0001E\u0001E\u0001E\u0001E\u0001"+ - "E\u0003E\u0435\bE\u0001E\u0001E\u0001E\u0001E\u0003E\u043b\bE\u0001F\u0001"+ - "F\u0001F\u0001F\u0003F\u0441\bF\u0001F\u0003F\u0444\bF\u0001F\u0001F\u0001"+ - "G\u0001G\u0001G\u0003G\u044b\bG\u0001G\u0005G\u044e\bG\nG\fG\u0451\tG"+ - "\u0001G\u0001G\u0001G\u0001G\u0003G\u0457\bG\u0001G\u0001G\u0001G\u0001"+ - "G\u0001G\u0003G\u045e\bG\u0001G\u0001G\u0001G\u0001G\u0001G\u0003G\u0465"+ - "\bG\u0001G\u0003G\u0468\bG\u0001H\u0001H\u0001H\u0001H\u0001H\u0001I\u0005"+ - "I\u0470\bI\nI\fI\u0473\tI\u0001J\u0005J\u0476\bJ\nJ\fJ\u0479\tJ\u0001"+ - "J\u0001J\u0004J\u047d\bJ\u000bJ\fJ\u047e\u0001J\u0001J\u0003J\u0483\b"+ - "J\u0001K\u0001K\u0001K\u0001K\u0005K\u0489\bK\nK\fK\u048c\tK\u0001K\u0003"+ - "K\u048f\bK\u0001K\u0000\u0000L\u0000\u0002\u0004\u0006\b\n\f\u000e\u0010"+ - "\u0012\u0014\u0016\u0018\u001a\u001c\u001e \"$&(*,.02468:<>@BDFHJLNPR"+ - "TVXZ\\^`bdfhjlnprtvxz|~\u0080\u0082\u0084\u0086\u0088\u008a\u008c\u008e"+ - "\u0090\u0092\u0094\u0096\u0000\u0004\u0001\u0000\u0004\u0005\u0001\u0000"+ - "\u0003\u0005\u0002\u0000\u0003\u0003\u00a8\u00a8\u0001\u0000\u0096\u0097"+ - "\u0519\u0000\u0098\u0001\u0000\u0000\u0000\u0002\u009a\u0001\u0000\u0000"+ - "\u0000\u0004\u009c\u0001\u0000\u0000\u0000\u0006\u00ab\u0001\u0000\u0000"+ - "\u0000\b\u00ad\u0001\u0000\u0000\u0000\n\u00b2\u0001\u0000\u0000\u0000"+ - "\f\u00b7\u0001\u0000\u0000\u0000\u000e\u00bf\u0001\u0000\u0000\u0000\u0010"+ - "\u00cb\u0001\u0000\u0000\u0000\u0012\u00dd\u0001\u0000\u0000\u0000\u0014"+ - "\u00eb\u0001\u0000\u0000\u0000\u0016\u00ee\u0001\u0000\u0000\u0000\u0018"+ - "\u00f1\u0001\u0000\u0000\u0000\u001a\u00f7\u0001\u0000\u0000\u0000\u001c"+ - "\u00fb\u0001\u0000\u0000\u0000\u001e\u0100\u0001\u0000\u0000\u0000 \u0102"+ - "\u0001\u0000\u0000\u0000\"\u0104\u0001\u0000\u0000\u0000$\u010b\u0001"+ - "\u0000\u0000\u0000&\u010d\u0001\u0000\u0000\u0000(\u0165\u0001\u0000\u0000"+ - "\u0000*\u0167\u0001\u0000\u0000\u0000,\u016f\u0001\u0000\u0000\u0000."+ - "\u0175\u0001\u0000\u0000\u00000\u0178\u0001\u0000\u0000\u00002\u017b\u0001"+ - "\u0000\u0000\u00004\u0182\u0001\u0000\u0000\u00006\u0187\u0001\u0000\u0000"+ - "\u00008\u0194\u0001\u0000\u0000\u0000:\u01a1\u0001\u0000\u0000\u0000<"+ - "\u01bd\u0001\u0000\u0000\u0000>\u01cd\u0001\u0000\u0000\u0000@\u01fa\u0001"+ - "\u0000\u0000\u0000B\u0207\u0001\u0000\u0000\u0000D\u0209\u0001\u0000\u0000"+ - "\u0000F\u020c\u0001\u0000\u0000\u0000H\u023a\u0001\u0000\u0000\u0000J"+ - "\u023d\u0001\u0000\u0000\u0000L\u024c\u0001\u0000\u0000\u0000N\u025c\u0001"+ - "\u0000\u0000\u0000P\u0268\u0001\u0000\u0000\u0000R\u026e\u0001\u0000\u0000"+ - "\u0000T\u0270\u0001\u0000\u0000\u0000V\u0285\u0001\u0000\u0000\u0000X"+ - "\u0287\u0001\u0000\u0000\u0000Z\u029a\u0001\u0000\u0000\u0000\\\u02a5"+ - "\u0001\u0000\u0000\u0000^\u02d3\u0001\u0000\u0000\u0000`\u02d5\u0001\u0000"+ - "\u0000\u0000b\u02ef\u0001\u0000\u0000\u0000d\u030f\u0001\u0000\u0000\u0000"+ - "f\u0311\u0001\u0000\u0000\u0000h\u0329\u0001\u0000\u0000\u0000j\u032b"+ - "\u0001\u0000\u0000\u0000l\u033c\u0001\u0000\u0000\u0000n\u0366\u0001\u0000"+ - "\u0000\u0000p\u0368\u0001\u0000\u0000\u0000r\u036f\u0001\u0000\u0000\u0000"+ - "t\u0389\u0001\u0000\u0000\u0000v\u038b\u0001\u0000\u0000\u0000x\u0391"+ - "\u0001\u0000\u0000\u0000z\u0396\u0001\u0000\u0000\u0000|\u039f\u0001\u0000"+ - "\u0000\u0000~\u03a7\u0001\u0000\u0000\u0000\u0080\u03b7\u0001\u0000\u0000"+ - "\u0000\u0082\u03b9\u0001\u0000\u0000\u0000\u0084\u03e2\u0001\u0000\u0000"+ - "\u0000\u0086\u03f5\u0001\u0000\u0000\u0000\u0088\u042b\u0001\u0000\u0000"+ - "\u0000\u008a\u043a\u0001\u0000\u0000\u0000\u008c\u043c\u0001\u0000\u0000"+ - "\u0000\u008e\u0467\u0001\u0000\u0000\u0000\u0090\u0469\u0001\u0000\u0000"+ - "\u0000\u0092\u0471\u0001\u0000\u0000\u0000\u0094\u0482\u0001\u0000\u0000"+ - "\u0000\u0096\u048e\u0001\u0000\u0000\u0000\u0098\u0099\u0007\u0000\u0000"+ - "\u0000\u0099\u0001\u0001\u0000\u0000\u0000\u009a\u009b\u0005\u0006\u0000"+ - "\u0000\u009b\u0003\u0001\u0000\u0000\u0000\u009c\u009d\u0005\u0007\u0000"+ - "\u0000\u009d\u0005\u0001\u0000\u0000\u0000\u009e\u00ac\u0005\n\u0000\u0000"+ - "\u009f\u00ac\u0005\u000b\u0000\u0000\u00a0\u00a1\u0005\u0001\u0000\u0000"+ - "\u00a1\u00a2\u0005\r\u0000\u0000\u00a2\u00a3\u0003 \u0010\u0000\u00a3"+ - "\u00a4\u0005\u0002\u0000\u0000\u00a4\u00ac\u0001\u0000\u0000\u0000\u00a5"+ - "\u00a6\u0005\u0001\u0000\u0000\u00a6\u00a7\u0005\r\u0000\u0000\u00a7\u00a8"+ - "\u0005\u000f\u0000\u0000\u00a8\u00a9\u0003 \u0010\u0000\u00a9\u00aa\u0005"+ - "\u0002\u0000\u0000\u00aa\u00ac\u0001\u0000\u0000\u0000\u00ab\u009e\u0001"+ - "\u0000\u0000\u0000\u00ab\u009f\u0001\u0000\u0000\u0000\u00ab\u00a0\u0001"+ - "\u0000\u0000\u0000\u00ab\u00a5\u0001\u0000\u0000\u0000\u00ac\u0007\u0001"+ - "\u0000\u0000\u0000\u00ad\u00ae\u0005\u00a9\u0000\u0000\u00ae\t\u0001\u0000"+ - "\u0000\u0000\u00af\u00b3\u0003\u0004\u0002\u0000\u00b0\u00b3\u0003\b\u0004"+ - "\u0000\u00b1\u00b3\u0003\u0006\u0003\u0000\u00b2\u00af\u0001\u0000\u0000"+ - "\u0000\u00b2\u00b0\u0001\u0000\u0000\u0000\u00b2\u00b1\u0001\u0000\u0000"+ - "\u0000\u00b3\u000b\u0001\u0000\u0000\u0000\u00b4\u00b8\u0005\u0085\u0000"+ - "\u0000\u00b5\u00b8\u0005\u0086\u0000\u0000\u00b6\u00b8\u0003\u0016\u000b"+ - "\u0000\u00b7\u00b4\u0001\u0000\u0000\u0000\u00b7\u00b5\u0001\u0000\u0000"+ - "\u0000\u00b7\u00b6\u0001\u0000\u0000\u0000\u00b8\r\u0001\u0000\u0000\u0000"+ - "\u00b9\u00c0\u0003\n\u0005\u0000\u00ba\u00bb\u0005\u0001\u0000\u0000\u00bb"+ - "\u00bc\u0005\f\u0000\u0000\u00bc\u00bd\u0003\n\u0005\u0000\u00bd\u00be"+ - "\u0005\u0002\u0000\u0000\u00be\u00c0\u0001\u0000\u0000\u0000\u00bf\u00b9"+ - "\u0001\u0000\u0000\u0000\u00bf\u00ba\u0001\u0000\u0000\u0000\u00c0\u000f"+ - "\u0001\u0000\u0000\u0000\u00c1\u00c2\u0005\u0001\u0000\u0000\u00c2\u00c3"+ - "\u0005\u0085\u0000\u0000\u00c3\u00c4\u0003\u0016\u000b\u0000\u00c4\u00c5"+ - "\u0005\u0002\u0000\u0000\u00c5\u00cc\u0001\u0000\u0000\u0000\u00c6\u00c7"+ - "\u0005\u0001\u0000\u0000\u00c7\u00c8\u0005\u000e\u0000\u0000\u00c8\u00c9"+ - "\u0003 \u0010\u0000\u00c9\u00ca\u0005\u0002\u0000\u0000\u00ca\u00cc\u0001"+ - "\u0000\u0000\u0000\u00cb\u00c1\u0001\u0000\u0000\u0000\u00cb\u00c6\u0001"+ - "\u0000\u0000\u0000\u00cc\u0011\u0001\u0000\u0000\u0000\u00cd\u00ce\u0005"+ - "\u0001\u0000\u0000\u00ce\u00d8\u0005\u0088\u0000\u0000\u00cf\u00d1\u0003"+ - "\n\u0005\u0000\u00d0\u00cf\u0001\u0000\u0000\u0000\u00d1\u00d4\u0001\u0000"+ - "\u0000\u0000\u00d2\u00d0\u0001\u0000\u0000\u0000\u00d2\u00d3\u0001\u0000"+ - "\u0000\u0000\u00d3\u00d9\u0001\u0000\u0000\u0000\u00d4\u00d2\u0001\u0000"+ - "\u0000\u0000\u00d5\u00d6\u0003\"\u0011\u0000\u00d6\u00d7\u0003\n\u0005"+ - "\u0000\u00d7\u00d9\u0001\u0000\u0000\u0000\u00d8\u00d2\u0001\u0000\u0000"+ - "\u0000\u00d8\u00d5\u0001\u0000\u0000\u0000\u00d9\u00da\u0001\u0000\u0000"+ - "\u0000\u00da\u00dc\u0005\u0002\u0000\u0000\u00db\u00cd\u0001\u0000\u0000"+ - "\u0000\u00dc\u00df\u0001\u0000\u0000\u0000\u00dd\u00db\u0001\u0000\u0000"+ - "\u0000\u00dd\u00de\u0001\u0000\u0000\u0000\u00de\u0013\u0001\u0000\u0000"+ - "\u0000\u00df\u00dd\u0001\u0000\u0000\u0000\u00e0\u00e1\u0005\u0001\u0000"+ - "\u0000\u00e1\u00e5\u0005\u0089\u0000\u0000\u00e2\u00e4\u0003\n\u0005\u0000"+ - "\u00e3\u00e2\u0001\u0000\u0000\u0000\u00e4\u00e7\u0001\u0000\u0000\u0000"+ - "\u00e5\u00e3\u0001\u0000\u0000\u0000\u00e5\u00e6\u0001\u0000\u0000\u0000"+ - "\u00e6\u00e8\u0001\u0000\u0000\u0000\u00e7\u00e5\u0001\u0000\u0000\u0000"+ - "\u00e8\u00ea\u0005\u0002\u0000\u0000\u00e9\u00e0\u0001\u0000\u0000\u0000"+ - "\u00ea\u00ed\u0001\u0000\u0000\u0000\u00eb\u00e9\u0001\u0000\u0000\u0000"+ - "\u00eb\u00ec\u0001\u0000\u0000\u0000\u00ec\u0015\u0001\u0000\u0000\u0000"+ - "\u00ed\u00eb\u0001\u0000\u0000\u0000\u00ee\u00ef\u0003\u0012\t\u0000\u00ef"+ - "\u00f0\u0003\u0014\n\u0000\u00f0\u0017\u0001\u0000\u0000\u0000\u00f1\u00f3"+ - "\u0005\u0003\u0000\u0000\u00f2\u00f4\u0005\u0003\u0000\u0000\u00f3\u00f2"+ - "\u0001\u0000\u0000\u0000\u00f3\u00f4\u0001\u0000\u0000\u0000\u00f4\u00f5"+ - "\u0001\u0000\u0000\u0000\u00f5\u00f6\u0003\u0006\u0003\u0000\u00f6\u0019"+ - "\u0001\u0000\u0000\u0000\u00f7\u00f9\u0005\u0003\u0000\u0000\u00f8\u00fa"+ - "\u0005\u0003\u0000\u0000\u00f9\u00f8\u0001\u0000\u0000\u0000\u00f9\u00fa"+ - "\u0001\u0000\u0000\u0000\u00fa\u001b\u0001\u0000\u0000\u0000\u00fb\u00fc"+ - "\u0005\u0001\u0000\u0000\u00fc\u00fd\u0005\u0084\u0000\u0000\u00fd\u00fe"+ - "\u0003 \u0010\u0000\u00fe\u00ff\u0005\u0002\u0000\u0000\u00ff\u001d\u0001"+ - "\u0000\u0000\u0000\u0100\u0101\u0007\u0001\u0000\u0000\u0101\u001f\u0001"+ - "\u0000\u0000\u0000\u0102\u0103\u0007\u0002\u0000\u0000\u0103!\u0001\u0000"+ - "\u0000\u0000\u0104\u0105\u0005\u00a8\u0000\u0000\u0105#\u0001\u0000\u0000"+ - "\u0000\u0106\u010c\u0003(\u0014\u0000\u0107\u010c\u0003@ \u0000\u0108"+ - "\u010c\u0003F#\u0000\u0109\u010c\u0003*\u0015\u0000\u010a\u010c\u0003"+ - "&\u0013\u0000\u010b\u0106\u0001\u0000\u0000\u0000\u010b\u0107\u0001\u0000"+ - "\u0000\u0000\u010b\u0108\u0001\u0000\u0000\u0000\u010b\u0109\u0001\u0000"+ - "\u0000\u0000\u010b\u010a\u0001\u0000\u0000\u0000\u010c%\u0001\u0000\u0000"+ - "\u0000\u010d\u010e\u0005\u0018\u0000\u0000\u010e\u010f\u0005\u0001\u0000"+ - "\u0000\u010f\u0110\u0003P(\u0000\u0110\u0111\u0005\u0019\u0000\u0000\u0111"+ - "\u0112\u0003P(\u0000\u0112\u0113\u0005\u0019\u0000\u0000\u0113\u0114\u0003"+ - "P(\u0000\u0114\u0115\u0005\u0002\u0000\u0000\u0115\u0116\u0003P(\u0000"+ + "D\u0003D\u040c\bD\u0001E\u0001E\u0001E\u0001E\u0001E\u0001E\u0001E\u0003"+ + "E\u0415\bE\u0001E\u0001E\u0001E\u0001E\u0003E\u041b\bE\u0001F\u0001F\u0001"+ + "F\u0001F\u0003F\u0421\bF\u0001F\u0003F\u0424\bF\u0001F\u0001F\u0001G\u0001"+ + "G\u0001G\u0003G\u042b\bG\u0001G\u0005G\u042e\bG\nG\fG\u0431\tG\u0001G"+ + "\u0001G\u0001G\u0001G\u0003G\u0437\bG\u0001G\u0001G\u0001G\u0001G\u0001"+ + "G\u0003G\u043e\bG\u0001G\u0001G\u0001G\u0001G\u0001G\u0003G\u0445\bG\u0001"+ + "G\u0003G\u0448\bG\u0001H\u0001H\u0001H\u0001H\u0001H\u0001I\u0005I\u0450"+ + "\bI\nI\fI\u0453\tI\u0001J\u0005J\u0456\bJ\nJ\fJ\u0459\tJ\u0001J\u0001"+ + "J\u0004J\u045d\bJ\u000bJ\fJ\u045e\u0001J\u0001J\u0003J\u0463\bJ\u0001"+ + "K\u0001K\u0001K\u0001K\u0005K\u0469\bK\nK\fK\u046c\tK\u0001K\u0003K\u046f"+ + "\bK\u0001K\u0000\u0000L\u0000\u0002\u0004\u0006\b\n\f\u000e\u0010\u0012"+ + "\u0014\u0016\u0018\u001a\u001c\u001e \"$&(*,.02468:<>@BDFHJLNPRTVXZ\\"+ + "^`bdfhjlnprtvxz|~\u0080\u0082\u0084\u0086\u0088\u008a\u008c\u008e\u0090"+ + "\u0092\u0094\u0096\u0000\u0004\u0001\u0000\u0004\u0005\u0001\u0000\u0003"+ + "\u0005\u0002\u0000\u0003\u0003\u00a8\u00a8\u0001\u0000\u0096\u0097\u04f2"+ + "\u0000\u0098\u0001\u0000\u0000\u0000\u0002\u009a\u0001\u0000\u0000\u0000"+ + "\u0004\u009c\u0001\u0000\u0000\u0000\u0006\u00ab\u0001\u0000\u0000\u0000"+ + "\b\u00ad\u0001\u0000\u0000\u0000\n\u00b2\u0001\u0000\u0000\u0000\f\u00b7"+ + "\u0001\u0000\u0000\u0000\u000e\u00bf\u0001\u0000\u0000\u0000\u0010\u00cb"+ + "\u0001\u0000\u0000\u0000\u0012\u00dd\u0001\u0000\u0000\u0000\u0014\u00eb"+ + "\u0001\u0000\u0000\u0000\u0016\u00ee\u0001\u0000\u0000\u0000\u0018\u00f1"+ + "\u0001\u0000\u0000\u0000\u001a\u00f7\u0001\u0000\u0000\u0000\u001c\u00fb"+ + "\u0001\u0000\u0000\u0000\u001e\u0100\u0001\u0000\u0000\u0000 \u0102\u0001"+ + "\u0000\u0000\u0000\"\u0104\u0001\u0000\u0000\u0000$\u010b\u0001\u0000"+ + "\u0000\u0000&\u010d\u0001\u0000\u0000\u0000(\u0165\u0001\u0000\u0000\u0000"+ + "*\u0167\u0001\u0000\u0000\u0000,\u016f\u0001\u0000\u0000\u0000.\u0175"+ + "\u0001\u0000\u0000\u00000\u0178\u0001\u0000\u0000\u00002\u017b\u0001\u0000"+ + "\u0000\u00004\u0182\u0001\u0000\u0000\u00006\u0187\u0001\u0000\u0000\u0000"+ + "8\u0194\u0001\u0000\u0000\u0000:\u01a1\u0001\u0000\u0000\u0000<\u01bd"+ + "\u0001\u0000\u0000\u0000>\u01cd\u0001\u0000\u0000\u0000@\u01fa\u0001\u0000"+ + "\u0000\u0000B\u0207\u0001\u0000\u0000\u0000D\u0209\u0001\u0000\u0000\u0000"+ + "F\u020c\u0001\u0000\u0000\u0000H\u023a\u0001\u0000\u0000\u0000J\u023d"+ + "\u0001\u0000\u0000\u0000L\u024c\u0001\u0000\u0000\u0000N\u025c\u0001\u0000"+ + "\u0000\u0000P\u0268\u0001\u0000\u0000\u0000R\u026e\u0001\u0000\u0000\u0000"+ + "T\u0270\u0001\u0000\u0000\u0000V\u0285\u0001\u0000\u0000\u0000X\u0287"+ + "\u0001\u0000\u0000\u0000Z\u029a\u0001\u0000\u0000\u0000\\\u02a5\u0001"+ + "\u0000\u0000\u0000^\u02a7\u0001\u0000\u0000\u0000`\u02b5\u0001\u0000\u0000"+ + "\u0000b\u02cf\u0001\u0000\u0000\u0000d\u02ef\u0001\u0000\u0000\u0000f"+ + "\u02f1\u0001\u0000\u0000\u0000h\u0309\u0001\u0000\u0000\u0000j\u030b\u0001"+ + "\u0000\u0000\u0000l\u031c\u0001\u0000\u0000\u0000n\u0346\u0001\u0000\u0000"+ + "\u0000p\u0348\u0001\u0000\u0000\u0000r\u034f\u0001\u0000\u0000\u0000t"+ + "\u0369\u0001\u0000\u0000\u0000v\u036b\u0001\u0000\u0000\u0000x\u0371\u0001"+ + "\u0000\u0000\u0000z\u0376\u0001\u0000\u0000\u0000|\u037f\u0001\u0000\u0000"+ + "\u0000~\u0387\u0001\u0000\u0000\u0000\u0080\u0397\u0001\u0000\u0000\u0000"+ + "\u0082\u0399\u0001\u0000\u0000\u0000\u0084\u03c2\u0001\u0000\u0000\u0000"+ + "\u0086\u03d5\u0001\u0000\u0000\u0000\u0088\u040b\u0001\u0000\u0000\u0000"+ + "\u008a\u041a\u0001\u0000\u0000\u0000\u008c\u041c\u0001\u0000\u0000\u0000"+ + "\u008e\u0447\u0001\u0000\u0000\u0000\u0090\u0449\u0001\u0000\u0000\u0000"+ + "\u0092\u0451\u0001\u0000\u0000\u0000\u0094\u0462\u0001\u0000\u0000\u0000"+ + "\u0096\u046e\u0001\u0000\u0000\u0000\u0098\u0099\u0007\u0000\u0000\u0000"+ + "\u0099\u0001\u0001\u0000\u0000\u0000\u009a\u009b\u0005\u0006\u0000\u0000"+ + "\u009b\u0003\u0001\u0000\u0000\u0000\u009c\u009d\u0005\u0007\u0000\u0000"+ + "\u009d\u0005\u0001\u0000\u0000\u0000\u009e\u00ac\u0005\n\u0000\u0000\u009f"+ + "\u00ac\u0005\u000b\u0000\u0000\u00a0\u00a1\u0005\u0001\u0000\u0000\u00a1"+ + "\u00a2\u0005\r\u0000\u0000\u00a2\u00a3\u0003 \u0010\u0000\u00a3\u00a4"+ + "\u0005\u0002\u0000\u0000\u00a4\u00ac\u0001\u0000\u0000\u0000\u00a5\u00a6"+ + "\u0005\u0001\u0000\u0000\u00a6\u00a7\u0005\r\u0000\u0000\u00a7\u00a8\u0005"+ + "\u000f\u0000\u0000\u00a8\u00a9\u0003 \u0010\u0000\u00a9\u00aa\u0005\u0002"+ + "\u0000\u0000\u00aa\u00ac\u0001\u0000\u0000\u0000\u00ab\u009e\u0001\u0000"+ + "\u0000\u0000\u00ab\u009f\u0001\u0000\u0000\u0000\u00ab\u00a0\u0001\u0000"+ + "\u0000\u0000\u00ab\u00a5\u0001\u0000\u0000\u0000\u00ac\u0007\u0001\u0000"+ + "\u0000\u0000\u00ad\u00ae\u0005\u00a9\u0000\u0000\u00ae\t\u0001\u0000\u0000"+ + "\u0000\u00af\u00b3\u0003\u0004\u0002\u0000\u00b0\u00b3\u0003\b\u0004\u0000"+ + "\u00b1\u00b3\u0003\u0006\u0003\u0000\u00b2\u00af\u0001\u0000\u0000\u0000"+ + "\u00b2\u00b0\u0001\u0000\u0000\u0000\u00b2\u00b1\u0001\u0000\u0000\u0000"+ + "\u00b3\u000b\u0001\u0000\u0000\u0000\u00b4\u00b8\u0005\u0085\u0000\u0000"+ + "\u00b5\u00b8\u0005\u0086\u0000\u0000\u00b6\u00b8\u0003\u0016\u000b\u0000"+ + "\u00b7\u00b4\u0001\u0000\u0000\u0000\u00b7\u00b5\u0001\u0000\u0000\u0000"+ + "\u00b7\u00b6\u0001\u0000\u0000\u0000\u00b8\r\u0001\u0000\u0000\u0000\u00b9"+ + "\u00c0\u0003\n\u0005\u0000\u00ba\u00bb\u0005\u0001\u0000\u0000\u00bb\u00bc"+ + "\u0005\f\u0000\u0000\u00bc\u00bd\u0003\n\u0005\u0000\u00bd\u00be\u0005"+ + "\u0002\u0000\u0000\u00be\u00c0\u0001\u0000\u0000\u0000\u00bf\u00b9\u0001"+ + "\u0000\u0000\u0000\u00bf\u00ba\u0001\u0000\u0000\u0000\u00c0\u000f\u0001"+ + "\u0000\u0000\u0000\u00c1\u00c2\u0005\u0001\u0000\u0000\u00c2\u00c3\u0005"+ + "\u0085\u0000\u0000\u00c3\u00c4\u0003\u0016\u000b\u0000\u00c4\u00c5\u0005"+ + "\u0002\u0000\u0000\u00c5\u00cc\u0001\u0000\u0000\u0000\u00c6\u00c7\u0005"+ + "\u0001\u0000\u0000\u00c7\u00c8\u0005\u000e\u0000\u0000\u00c8\u00c9\u0003"+ + " \u0010\u0000\u00c9\u00ca\u0005\u0002\u0000\u0000\u00ca\u00cc\u0001\u0000"+ + "\u0000\u0000\u00cb\u00c1\u0001\u0000\u0000\u0000\u00cb\u00c6\u0001\u0000"+ + "\u0000\u0000\u00cc\u0011\u0001\u0000\u0000\u0000\u00cd\u00ce\u0005\u0001"+ + "\u0000\u0000\u00ce\u00d8\u0005\u0088\u0000\u0000\u00cf\u00d1\u0003\n\u0005"+ + "\u0000\u00d0\u00cf\u0001\u0000\u0000\u0000\u00d1\u00d4\u0001\u0000\u0000"+ + "\u0000\u00d2\u00d0\u0001\u0000\u0000\u0000\u00d2\u00d3\u0001\u0000\u0000"+ + "\u0000\u00d3\u00d9\u0001\u0000\u0000\u0000\u00d4\u00d2\u0001\u0000\u0000"+ + "\u0000\u00d5\u00d6\u0003\"\u0011\u0000\u00d6\u00d7\u0003\n\u0005\u0000"+ + "\u00d7\u00d9\u0001\u0000\u0000\u0000\u00d8\u00d2\u0001\u0000\u0000\u0000"+ + "\u00d8\u00d5\u0001\u0000\u0000\u0000\u00d9\u00da\u0001\u0000\u0000\u0000"+ + "\u00da\u00dc\u0005\u0002\u0000\u0000\u00db\u00cd\u0001\u0000\u0000\u0000"+ + "\u00dc\u00df\u0001\u0000\u0000\u0000\u00dd\u00db\u0001\u0000\u0000\u0000"+ + "\u00dd\u00de\u0001\u0000\u0000\u0000\u00de\u0013\u0001\u0000\u0000\u0000"+ + "\u00df\u00dd\u0001\u0000\u0000\u0000\u00e0\u00e1\u0005\u0001\u0000\u0000"+ + "\u00e1\u00e5\u0005\u0089\u0000\u0000\u00e2\u00e4\u0003\n\u0005\u0000\u00e3"+ + "\u00e2\u0001\u0000\u0000\u0000\u00e4\u00e7\u0001\u0000\u0000\u0000\u00e5"+ + "\u00e3\u0001\u0000\u0000\u0000\u00e5\u00e6\u0001\u0000\u0000\u0000\u00e6"+ + "\u00e8\u0001\u0000\u0000\u0000\u00e7\u00e5\u0001\u0000\u0000\u0000\u00e8"+ + "\u00ea\u0005\u0002\u0000\u0000\u00e9\u00e0\u0001\u0000\u0000\u0000\u00ea"+ + "\u00ed\u0001\u0000\u0000\u0000\u00eb\u00e9\u0001\u0000\u0000\u0000\u00eb"+ + "\u00ec\u0001\u0000\u0000\u0000\u00ec\u0015\u0001\u0000\u0000\u0000\u00ed"+ + "\u00eb\u0001\u0000\u0000\u0000\u00ee\u00ef\u0003\u0012\t\u0000\u00ef\u00f0"+ + "\u0003\u0014\n\u0000\u00f0\u0017\u0001\u0000\u0000\u0000\u00f1\u00f3\u0005"+ + "\u0003\u0000\u0000\u00f2\u00f4\u0005\u0003\u0000\u0000\u00f3\u00f2\u0001"+ + "\u0000\u0000\u0000\u00f3\u00f4\u0001\u0000\u0000\u0000\u00f4\u00f5\u0001"+ + "\u0000\u0000\u0000\u00f5\u00f6\u0003\u0006\u0003\u0000\u00f6\u0019\u0001"+ + "\u0000\u0000\u0000\u00f7\u00f9\u0005\u0003\u0000\u0000\u00f8\u00fa\u0005"+ + "\u0003\u0000\u0000\u00f9\u00f8\u0001\u0000\u0000\u0000\u00f9\u00fa\u0001"+ + "\u0000\u0000\u0000\u00fa\u001b\u0001\u0000\u0000\u0000\u00fb\u00fc\u0005"+ + "\u0001\u0000\u0000\u00fc\u00fd\u0005\u0084\u0000\u0000\u00fd\u00fe\u0003"+ + " \u0010\u0000\u00fe\u00ff\u0005\u0002\u0000\u0000\u00ff\u001d\u0001\u0000"+ + "\u0000\u0000\u0100\u0101\u0007\u0001\u0000\u0000\u0101\u001f\u0001\u0000"+ + "\u0000\u0000\u0102\u0103\u0007\u0002\u0000\u0000\u0103!\u0001\u0000\u0000"+ + "\u0000\u0104\u0105\u0005\u00a8\u0000\u0000\u0105#\u0001\u0000\u0000\u0000"+ + "\u0106\u010c\u0003(\u0014\u0000\u0107\u010c\u0003@ \u0000\u0108\u010c"+ + "\u0003F#\u0000\u0109\u010c\u0003*\u0015\u0000\u010a\u010c\u0003&\u0013"+ + "\u0000\u010b\u0106\u0001\u0000\u0000\u0000\u010b\u0107\u0001\u0000\u0000"+ + "\u0000\u010b\u0108\u0001\u0000\u0000\u0000\u010b\u0109\u0001\u0000\u0000"+ + "\u0000\u010b\u010a\u0001\u0000\u0000\u0000\u010c%\u0001\u0000\u0000\u0000"+ + "\u010d\u010e\u0005\u0018\u0000\u0000\u010e\u010f\u0005\u0001\u0000\u0000"+ + "\u010f\u0110\u0003P(\u0000\u0110\u0111\u0005\u0019\u0000\u0000\u0111\u0112"+ + "\u0003P(\u0000\u0112\u0113\u0005\u0019\u0000\u0000\u0113\u0114\u0003P"+ + "(\u0000\u0114\u0115\u0005\u0002\u0000\u0000\u0115\u0116\u0003P(\u0000"+ "\u0116\'\u0001\u0000\u0000\u0000\u0117\u0166\u0005\u0014\u0000\u0000\u0118"+ "\u0166\u0005\u0010\u0000\u0000\u0119\u0166\u0005\u0015\u0000\u0000\u011a"+ "\u0166\u00036\u001b\u0000\u011b\u011c\u0005\u001b\u0000\u0000\u011c\u0166"+ @@ -7700,297 +7596,277 @@ public final ModuleContext module() throws RecognitionException { "\u0000\u0000\u02a3\u02a6\u0001\u0000\u0000\u0000\u02a4\u02a6\u0003H$\u0000"+ "\u02a5\u029f\u0001\u0000\u0000\u0000\u02a5\u02a4\u0001\u0000\u0000\u0000"+ "\u02a6]\u0001\u0000\u0000\u0000\u02a7\u02a8\u0005\u0001\u0000\u0000\u02a8"+ - "\u02aa\u0005\u008e\u0000\u0000\u02a9\u02ab\u0003 \u0010\u0000\u02aa\u02a9"+ - "\u0001\u0000\u0000\u0000\u02aa\u02ab\u0001\u0000\u0000\u0000\u02ab\u02ac"+ - "\u0001\u0000\u0000\u0000\u02ac\u02ad\u0005\u0001\u0000\u0000\u02ad\u02ae"+ - "\u0003$\u0012\u0000\u02ae\u02b2\u0005\u0002\u0000\u0000\u02af\u02b1\u0003"+ - " \u0010\u0000\u02b0\u02af\u0001\u0000\u0000\u0000\u02b1\u02b4\u0001\u0000"+ - "\u0000\u0000\u02b2\u02b0\u0001\u0000\u0000\u0000\u02b2\u02b3\u0001\u0000"+ - "\u0000\u0000\u02b3\u02b5\u0001\u0000\u0000\u0000\u02b4\u02b2\u0001\u0000"+ - "\u0000\u0000\u02b5\u02b6\u0005\u0002\u0000\u0000\u02b6\u02d4\u0001\u0000"+ - "\u0000\u0000\u02b7\u02b8\u0005\u0001\u0000\u0000\u02b8\u02ba\u0005\u008e"+ - "\u0000\u0000\u02b9\u02bb\u0003 \u0010\u0000\u02ba\u02b9\u0001\u0000\u0000"+ - "\u0000\u02ba\u02bb\u0001\u0000\u0000\u0000\u02bb\u02bc\u0001\u0000\u0000"+ - "\u0000\u02bc\u02c0\u0003\\.\u0000\u02bd\u02bf\u0003 \u0010\u0000\u02be"+ - "\u02bd\u0001\u0000\u0000\u0000\u02bf\u02c2\u0001\u0000\u0000\u0000\u02c0"+ - "\u02be\u0001\u0000\u0000\u0000\u02c0\u02c1\u0001\u0000\u0000\u0000\u02c1"+ - "\u02c3\u0001\u0000\u0000\u0000\u02c2\u02c0\u0001\u0000\u0000\u0000\u02c3"+ - "\u02c4\u0005\u0002\u0000\u0000\u02c4\u02d4\u0001\u0000\u0000\u0000\u02c5"+ - "\u02c6\u0005\u0001\u0000\u0000\u02c6\u02c8\u0005\u008e\u0000\u0000\u02c7"+ - "\u02c9\u0003 \u0010\u0000\u02c8\u02c7\u0001\u0000\u0000\u0000\u02c8\u02c9"+ - "\u0001\u0000\u0000\u0000\u02c9\u02ca\u0001\u0000\u0000\u0000\u02ca\u02cb"+ - "\u0005\u0094\u0000\u0000\u02cb\u02cf\u0005\u0085\u0000\u0000\u02cc\u02ce"+ - "\u0003 \u0010\u0000\u02cd\u02cc\u0001\u0000\u0000\u0000\u02ce\u02d1\u0001"+ - "\u0000\u0000\u0000\u02cf\u02cd\u0001\u0000\u0000\u0000\u02cf\u02d0\u0001"+ - "\u0000\u0000\u0000\u02d0\u02d2\u0001\u0000\u0000\u0000\u02d1\u02cf\u0001"+ - "\u0000\u0000\u0000\u02d2\u02d4\u0005\u0002\u0000\u0000\u02d3\u02a7\u0001"+ - "\u0000\u0000\u0000\u02d3\u02b7\u0001\u0000\u0000\u0000\u02d3\u02c5\u0001"+ - "\u0000\u0000\u0000\u02d4_\u0001\u0000\u0000\u0000\u02d5\u02d6\u0005\u0001"+ - "\u0000\u0000\u02d6\u02d8\u0005\u008c\u0000\u0000\u02d7\u02d9\u0003\"\u0011"+ - "\u0000\u02d8\u02d7\u0001\u0000\u0000\u0000\u02d8\u02d9\u0001\u0000\u0000"+ - "\u0000\u02d9\u02da\u0001\u0000\u0000\u0000\u02da\u02db\u0003b1\u0000\u02db"+ - "\u02dc\u0005\u0002\u0000\u0000\u02dca\u0001\u0000\u0000\u0000\u02dd\u02f0"+ - "\u0003\u0018\f\u0000\u02de\u02df\u0003r9\u0000\u02df\u02e0\u0003\u0018"+ - "\f\u0000\u02e0\u02f0\u0001\u0000\u0000\u0000\u02e1\u02e2\u0003x<\u0000"+ - "\u02e2\u02e3\u0003b1\u0000\u02e3\u02f0\u0001\u0000\u0000\u0000\u02e4\u02e5"+ - "\u0003\u0006\u0003\u0000\u02e5\u02e6\u0005\u0001\u0000\u0000\u02e6\u02ea"+ - "\u0005\u008e\u0000\u0000\u02e7\u02e9\u0003 \u0010\u0000\u02e8\u02e7\u0001"+ - "\u0000\u0000\u0000\u02e9\u02ec\u0001\u0000\u0000\u0000\u02ea\u02e8\u0001"+ - "\u0000\u0000\u0000\u02ea\u02eb\u0001\u0000\u0000\u0000\u02eb\u02ed\u0001"+ - "\u0000\u0000\u0000\u02ec\u02ea\u0001\u0000\u0000\u0000\u02ed\u02ee\u0005"+ - "\u0002\u0000\u0000\u02ee\u02f0\u0001\u0000\u0000\u0000\u02ef\u02dd\u0001"+ - "\u0000\u0000\u0000\u02ef\u02de\u0001\u0000\u0000\u0000\u02ef\u02e1\u0001"+ - "\u0000\u0000\u0000\u02ef\u02e4\u0001\u0000\u0000\u0000\u02f0c\u0001\u0000"+ - "\u0000\u0000\u02f1\u02f2\u0005\u0001\u0000\u0000\u02f2\u02f4\u0005\u008f"+ - "\u0000\u0000\u02f3\u02f5\u0003 \u0010\u0000\u02f4\u02f3\u0001\u0000\u0000"+ - "\u0000\u02f4\u02f5\u0001\u0000\u0000\u0000\u02f5\u02f6\u0001\u0000\u0000"+ - "\u0000\u02f6\u02f7\u0005\u0001\u0000\u0000\u02f7\u02f8\u0003$\u0012\u0000"+ - "\u02f8\u02fc\u0005\u0002\u0000\u0000\u02f9\u02fb\u0005\u0006\u0000\u0000"+ - "\u02fa\u02f9\u0001\u0000\u0000\u0000\u02fb\u02fe\u0001\u0000\u0000\u0000"+ - "\u02fc\u02fa\u0001\u0000\u0000\u0000\u02fc\u02fd\u0001\u0000\u0000\u0000"+ - "\u02fd\u02ff\u0001\u0000\u0000\u0000\u02fe\u02fc\u0001\u0000\u0000\u0000"+ - "\u02ff\u0300\u0005\u0002\u0000\u0000\u0300\u0310\u0001\u0000\u0000\u0000"+ - "\u0301\u0302\u0005\u0001\u0000\u0000\u0302\u0304\u0005\u008f\u0000\u0000"+ - "\u0303\u0305\u0003 \u0010\u0000\u0304\u0303\u0001\u0000\u0000\u0000\u0304"+ - "\u0305\u0001\u0000\u0000\u0000\u0305\u0306\u0001\u0000\u0000\u0000\u0306"+ - "\u030a\u0003\\.\u0000\u0307\u0309\u0005\u0006\u0000\u0000\u0308\u0307"+ - "\u0001\u0000\u0000\u0000\u0309\u030c\u0001\u0000\u0000\u0000\u030a\u0308"+ - "\u0001\u0000\u0000\u0000\u030a\u030b\u0001\u0000\u0000\u0000\u030b\u030d"+ - "\u0001\u0000\u0000\u0000\u030c\u030a\u0001\u0000\u0000\u0000\u030d\u030e"+ - "\u0005\u0002\u0000\u0000\u030e\u0310\u0001\u0000\u0000\u0000\u030f\u02f1"+ - "\u0001\u0000\u0000\u0000\u030f\u0301\u0001\u0000\u0000\u0000\u0310e\u0001"+ - "\u0000\u0000\u0000\u0311\u0312\u0005\u0001\u0000\u0000\u0312\u0314\u0005"+ - "\u008d\u0000\u0000\u0313\u0315\u0003\"\u0011\u0000\u0314\u0313\u0001\u0000"+ - "\u0000\u0000\u0314\u0315\u0001\u0000\u0000\u0000\u0315\u0316\u0001\u0000"+ - "\u0000\u0000\u0316\u0317\u0003h4\u0000\u0317\u0318\u0005\u0002\u0000\u0000"+ - "\u0318g\u0001\u0000\u0000\u0000\u0319\u032a\u0003\u001a\r\u0000\u031a"+ - "\u031b\u0003r9\u0000\u031b\u031c\u0003\u001a\r\u0000\u031c\u032a\u0001"+ - "\u0000\u0000\u0000\u031d\u031e\u0003x<\u0000\u031e\u031f\u0003h4\u0000"+ - "\u031f\u032a\u0001\u0000\u0000\u0000\u0320\u0321\u0005\u0001\u0000\u0000"+ - "\u0321\u0325\u0005\u008f\u0000\u0000\u0322\u0324\u0005\u0006\u0000\u0000"+ - "\u0323\u0322\u0001\u0000\u0000\u0000\u0324\u0327\u0001\u0000\u0000\u0000"+ - "\u0325\u0323\u0001\u0000\u0000\u0000\u0325\u0326\u0001\u0000\u0000\u0000"+ - "\u0326\u0328\u0001\u0000\u0000\u0000\u0327\u0325\u0001\u0000\u0000\u0000"+ - "\u0328\u032a\u0005\u0002\u0000\u0000\u0329\u0319\u0001\u0000\u0000\u0000"+ - "\u0329\u031a\u0001\u0000\u0000\u0000\u0329\u031d\u0001\u0000\u0000\u0000"+ - "\u0329\u0320\u0001\u0000\u0000\u0000\u032ai\u0001\u0000\u0000\u0000\u032b"+ - "\u032c\u0005\u0001\u0000\u0000\u032c\u032e\u0005\u008b\u0000\u0000\u032d"+ - "\u032f\u0003\"\u0011\u0000\u032e\u032d\u0001\u0000\u0000\u0000\u032e\u032f"+ - "\u0001\u0000\u0000\u0000\u032f\u0330\u0001\u0000\u0000\u0000\u0330\u0331"+ - "\u0003l6\u0000\u0331\u0332\u0005\u0002\u0000\u0000\u0332k\u0001\u0000"+ - "\u0000\u0000\u0333\u0334\u0003\u000e\u0007\u0000\u0334\u0335\u0003R)\u0000"+ - "\u0335\u033d\u0001\u0000\u0000\u0000\u0336\u0337\u0003r9\u0000\u0337\u0338"+ - "\u0003\u000e\u0007\u0000\u0338\u033d\u0001\u0000\u0000\u0000\u0339\u033a"+ - "\u0003x<\u0000\u033a\u033b\u0003l6\u0000\u033b\u033d\u0001\u0000\u0000"+ - "\u0000\u033c\u0333\u0001\u0000\u0000\u0000\u033c\u0336\u0001\u0000\u0000"+ - "\u0000\u033c\u0339\u0001\u0000\u0000\u0000\u033dm\u0001\u0000\u0000\u0000"+ - "\u033e\u033f\u0005\u0001\u0000\u0000\u033f\u0341\u0005\u0085\u0000\u0000"+ - "\u0340\u0342\u0003\"\u0011\u0000\u0341\u0340\u0001\u0000\u0000\u0000\u0341"+ - "\u0342\u0001\u0000\u0000\u0000\u0342\u0343\u0001\u0000\u0000\u0000\u0343"+ - "\u0344\u0003\u001c\u000e\u0000\u0344\u0345\u0005\u0002\u0000\u0000\u0345"+ - "\u0367\u0001\u0000\u0000\u0000\u0346\u0347\u0005\u0001\u0000\u0000\u0347"+ - "\u0349\u0005\u0085\u0000\u0000\u0348\u034a\u0003\"\u0011\u0000\u0349\u0348"+ - "\u0001\u0000\u0000\u0000\u0349\u034a\u0001\u0000\u0000\u0000\u034a\u034b"+ - "\u0001\u0000\u0000\u0000\u034b\u034c\u0003\u0016\u000b\u0000\u034c\u034d"+ - "\u0005\u0002\u0000\u0000\u034d\u0367\u0001\u0000\u0000\u0000\u034e\u034f"+ - "\u0005\u0001\u0000\u0000\u034f\u0351\u0005\u008c\u0000\u0000\u0350\u0352"+ - "\u0003\"\u0011\u0000\u0351\u0350\u0001\u0000\u0000\u0000\u0351\u0352\u0001"+ - "\u0000\u0000\u0000\u0352\u0353\u0001\u0000\u0000\u0000\u0353\u0354\u0003"+ - "\u0018\f\u0000\u0354\u0355\u0005\u0002\u0000\u0000\u0355\u0367\u0001\u0000"+ - "\u0000\u0000\u0356\u0357\u0005\u0001\u0000\u0000\u0357\u0359\u0005\u008d"+ - "\u0000\u0000\u0358\u035a\u0003\"\u0011\u0000\u0359\u0358\u0001\u0000\u0000"+ - "\u0000\u0359\u035a\u0001\u0000\u0000\u0000\u035a\u035b\u0001\u0000\u0000"+ - "\u0000\u035b\u035c\u0003\u001a\r\u0000\u035c\u035d\u0005\u0002\u0000\u0000"+ - "\u035d\u0367\u0001\u0000\u0000\u0000\u035e\u035f\u0005\u0001\u0000\u0000"+ - "\u035f\u0361\u0005\u008b\u0000\u0000\u0360\u0362\u0003\"\u0011\u0000\u0361"+ - "\u0360\u0001\u0000\u0000\u0000\u0361\u0362\u0001\u0000\u0000\u0000\u0362"+ - "\u0363\u0001\u0000\u0000\u0000\u0363\u0364\u0003\u000e\u0007\u0000\u0364"+ - "\u0365\u0005\u0002\u0000\u0000\u0365\u0367\u0001\u0000\u0000\u0000\u0366"+ - "\u033e\u0001\u0000\u0000\u0000\u0366\u0346\u0001\u0000\u0000\u0000\u0366"+ - "\u034e\u0001\u0000\u0000\u0000\u0366\u0356\u0001\u0000\u0000\u0000\u0366"+ - "\u035e\u0001\u0000\u0000\u0000\u0367o\u0001\u0000\u0000\u0000\u0368\u0369"+ - "\u0005\u0001\u0000\u0000\u0369\u036a\u0005\u0091\u0000\u0000\u036a\u036b"+ - "\u0003\u0002\u0001\u0000\u036b\u036c\u0003\u0002\u0001\u0000\u036c\u036d"+ - "\u0003n7\u0000\u036d\u036e\u0005\u0002\u0000\u0000\u036eq\u0001\u0000"+ - "\u0000\u0000\u036f\u0370\u0005\u0001\u0000\u0000\u0370\u0371\u0005\u0091"+ - "\u0000\u0000\u0371\u0372\u0003\u0002\u0001\u0000\u0372\u0373\u0003\u0002"+ - "\u0001\u0000\u0373\u0374\u0005\u0002\u0000\u0000\u0374s\u0001\u0000\u0000"+ - "\u0000\u0375\u0376\u0005\u0001\u0000\u0000\u0376\u0377\u0005\u0085\u0000"+ - "\u0000\u0377\u0378\u0003 \u0010\u0000\u0378\u0379\u0005\u0002\u0000\u0000"+ - "\u0379\u038a\u0001\u0000\u0000\u0000\u037a\u037b\u0005\u0001\u0000\u0000"+ - "\u037b\u037c\u0005\u008c\u0000\u0000\u037c\u037d\u0003 \u0010\u0000\u037d"+ - "\u037e\u0005\u0002\u0000\u0000\u037e\u038a\u0001\u0000\u0000\u0000\u037f"+ - "\u0380\u0005\u0001\u0000\u0000\u0380\u0381\u0005\u008d\u0000\u0000\u0381"+ - "\u0382\u0003 \u0010\u0000\u0382\u0383\u0005\u0002\u0000\u0000\u0383\u038a"+ - "\u0001\u0000\u0000\u0000\u0384\u0385\u0005\u0001\u0000\u0000\u0385\u0386"+ - "\u0005\u008b\u0000\u0000\u0386\u0387\u0003 \u0010\u0000\u0387\u0388\u0005"+ - "\u0002\u0000\u0000\u0388\u038a\u0001\u0000\u0000\u0000\u0389\u0375\u0001"+ - "\u0000\u0000\u0000\u0389\u037a\u0001\u0000\u0000\u0000\u0389\u037f\u0001"+ - "\u0000\u0000\u0000\u0389\u0384\u0001\u0000\u0000\u0000\u038au\u0001\u0000"+ - "\u0000\u0000\u038b\u038c\u0005\u0001\u0000\u0000\u038c\u038d\u0005\u0092"+ - "\u0000\u0000\u038d\u038e\u0003\u0002\u0001\u0000\u038e\u038f\u0003t:\u0000"+ - "\u038f\u0390\u0005\u0002\u0000\u0000\u0390w\u0001\u0000\u0000\u0000\u0391"+ - "\u0392\u0005\u0001\u0000\u0000\u0392\u0393\u0005\u0092\u0000\u0000\u0393"+ - "\u0394\u0003\u0002\u0001\u0000\u0394\u0395\u0005\u0002\u0000\u0000\u0395"+ - "y\u0001\u0000\u0000\u0000\u0396\u0397\u0005\u0001\u0000\u0000\u0397\u0399"+ - "\u0005\u0093\u0000\u0000\u0398\u039a\u0003\"\u0011\u0000\u0399\u0398\u0001"+ - "\u0000\u0000\u0000\u0399\u039a\u0001\u0000\u0000\u0000\u039a\u039b\u0001"+ - "\u0000\u0000\u0000\u039b\u039c\u0003\u001c\u000e\u0000\u039c\u039d\u0003"+ - "\u0016\u000b\u0000\u039d\u039e\u0005\u0002\u0000\u0000\u039e{\u0001\u0000"+ - "\u0000\u0000\u039f\u03a0\u0005\u0001\u0000\u0000\u03a0\u03a2\u0005\u0084"+ - "\u0000\u0000\u03a1\u03a3\u0003\"\u0011\u0000\u03a2\u03a1\u0001\u0000\u0000"+ - "\u0000\u03a2\u03a3\u0001\u0000\u0000\u0000\u03a3\u03a4\u0001\u0000\u0000"+ - "\u0000\u03a4\u03a5\u0003\u0010\b\u0000\u03a5\u03a6\u0005\u0002\u0000\u0000"+ - "\u03a6}\u0001\u0000\u0000\u0000\u03a7\u03a8\u0005\u0001\u0000\u0000\u03a8"+ - "\u03a9\u0005\u0087\u0000\u0000\u03a9\u03aa\u0003 \u0010\u0000\u03aa\u03ab"+ - "\u0005\u0002\u0000\u0000\u03ab\u007f\u0001\u0000\u0000\u0000\u03ac\u03b8"+ - "\u0003|>\u0000\u03ad\u03b8\u0003j5\u0000\u03ae\u03b8\u0003`0\u0000\u03af"+ - "\u03b8\u0003f3\u0000\u03b0\u03b8\u0003T*\u0000\u03b1\u03b8\u0003^/\u0000"+ - "\u03b2\u03b8\u0003d2\u0000\u03b3\u03b8\u0003~?\u0000\u03b4\u03b8\u0003"+ - "p8\u0000\u03b5\u03b8\u0003v;\u0000\u03b6\u03b8\u0003z=\u0000\u03b7\u03ac"+ - "\u0001\u0000\u0000\u0000\u03b7\u03ad\u0001\u0000\u0000\u0000\u03b7\u03ae"+ - "\u0001\u0000\u0000\u0000\u03b7\u03af\u0001\u0000\u0000\u0000\u03b7\u03b0"+ - "\u0001\u0000\u0000\u0000\u03b7\u03b1\u0001\u0000\u0000\u0000\u03b7\u03b2"+ - "\u0001\u0000\u0000\u0000\u03b7\u03b3\u0001\u0000\u0000\u0000\u03b7\u03b4"+ - "\u0001\u0000\u0000\u0000\u03b7\u03b5\u0001\u0000\u0000\u0000\u03b7\u03b6"+ - "\u0001\u0000\u0000\u0000\u03b8\u0081\u0001\u0000\u0000\u0000\u03b9\u03ba"+ - "\u0005\u0001\u0000\u0000\u03ba\u03bc\u0005\u0095\u0000\u0000\u03bb\u03bd"+ - "\u0005\u00a8\u0000\u0000\u03bc\u03bb\u0001\u0000\u0000\u0000\u03bc\u03bd"+ - "\u0001\u0000\u0000\u0000\u03bd\u03c1\u0001\u0000\u0000\u0000\u03be\u03c0"+ - "\u0003\u0080@\u0000\u03bf\u03be\u0001\u0000\u0000\u0000\u03c0\u03c3\u0001"+ - "\u0000\u0000\u0000\u03c1\u03bf\u0001\u0000\u0000\u0000\u03c1\u03c2\u0001"+ - "\u0000\u0000\u0000\u03c2\u03c4\u0001\u0000\u0000\u0000\u03c3\u03c1\u0001"+ - "\u0000\u0000\u0000\u03c4\u03c5\u0005\u0002\u0000\u0000\u03c5\u0083\u0001"+ - "\u0000\u0000\u0000\u03c6\u03e3\u0003\u0082A\u0000\u03c7\u03c8\u0005\u0001"+ - "\u0000\u0000\u03c8\u03ca\u0005\u0095\u0000\u0000\u03c9\u03cb\u0005\u00a8"+ - "\u0000\u0000\u03ca\u03c9\u0001\u0000\u0000\u0000\u03ca\u03cb\u0001\u0000"+ - "\u0000\u0000\u03cb\u03cc\u0001\u0000\u0000\u0000\u03cc\u03d0\u0007\u0003"+ - "\u0000\u0000\u03cd\u03cf\u0005\u0006\u0000\u0000\u03ce\u03cd\u0001\u0000"+ - "\u0000\u0000\u03cf\u03d2\u0001\u0000\u0000\u0000\u03d0\u03ce\u0001\u0000"+ - "\u0000\u0000\u03d0\u03d1\u0001\u0000\u0000\u0000\u03d1\u03d3\u0001\u0000"+ - "\u0000\u0000\u03d2\u03d0\u0001\u0000\u0000\u0000\u03d3\u03e3\u0005\u0002"+ - "\u0000\u0000\u03d4\u03d5\u0005\u0001\u0000\u0000\u03d5\u03d6\u0005\u0095"+ - "\u0000\u0000\u03d6\u03d8\u0005\u0098\u0000\u0000\u03d7\u03d9\u0005\u00a8"+ - "\u0000\u0000\u03d8\u03d7\u0001\u0000\u0000\u0000\u03d8\u03d9\u0001\u0000"+ - "\u0000\u0000\u03d9\u03da\u0001\u0000\u0000\u0000\u03da\u03de\u0005\u0096"+ - "\u0000\u0000\u03db\u03dd\u0005\u0006\u0000\u0000\u03dc\u03db\u0001\u0000"+ - "\u0000\u0000\u03dd\u03e0\u0001\u0000\u0000\u0000\u03de\u03dc\u0001\u0000"+ - "\u0000\u0000\u03de\u03df\u0001\u0000\u0000\u0000\u03df\u03e1\u0001\u0000"+ - "\u0000\u0000\u03e0\u03de\u0001\u0000\u0000\u0000\u03e1\u03e3\u0005\u0002"+ - "\u0000\u0000\u03e2\u03c6\u0001\u0000\u0000\u0000\u03e2\u03c7\u0001\u0000"+ - "\u0000\u0000\u03e2\u03d4\u0001\u0000\u0000\u0000\u03e3\u0085\u0001\u0000"+ - "\u0000\u0000\u03e4\u03e5\u0005\u0001\u0000\u0000\u03e5\u03e7\u0005\u009c"+ - "\u0000\u0000\u03e6\u03e8\u0005\u00a8\u0000\u0000\u03e7\u03e6\u0001\u0000"+ - "\u0000\u0000\u03e7\u03e8\u0001\u0000\u0000\u0000\u03e8\u03e9\u0001\u0000"+ - "\u0000\u0000\u03e9\u03ea\u0003\u0002\u0001\u0000\u03ea\u03eb\u0003\u0092"+ - "I\u0000\u03eb\u03ec\u0005\u0002\u0000\u0000\u03ec\u03f6\u0001\u0000\u0000"+ - "\u0000\u03ed\u03ee\u0005\u0001\u0000\u0000\u03ee\u03f0\u0005\u009d\u0000"+ - "\u0000\u03ef\u03f1\u0005\u00a8\u0000\u0000\u03f0\u03ef\u0001\u0000\u0000"+ - "\u0000\u03f0\u03f1\u0001\u0000\u0000\u0000\u03f1\u03f2\u0001\u0000\u0000"+ - "\u0000\u03f2\u03f3\u0003\u0002\u0001\u0000\u03f3\u03f4\u0005\u0002\u0000"+ - "\u0000\u03f4\u03f6\u0001\u0000\u0000\u0000\u03f5\u03e4\u0001\u0000\u0000"+ - "\u0000\u03f5\u03ed\u0001\u0000\u0000\u0000\u03f6\u0087\u0001\u0000\u0000"+ - "\u0000\u03f7\u03f8\u0005\u0001\u0000\u0000\u03f8\u03f9\u0005\u009e\u0000"+ - "\u0000\u03f9\u03fa\u0003\u0084B\u0000\u03fa\u03fb\u0005\u0006\u0000\u0000"+ - "\u03fb\u03fc\u0005\u0002\u0000\u0000\u03fc\u042c\u0001\u0000\u0000\u0000"+ - "\u03fd\u03fe\u0005\u0001\u0000\u0000\u03fe\u03ff\u0005\u009f\u0000\u0000"+ - "\u03ff\u0400\u0003\u0084B\u0000\u0400\u0401\u0005\u0006\u0000\u0000\u0401"+ - "\u0402\u0005\u0002\u0000\u0000\u0402\u042c\u0001\u0000\u0000\u0000\u0403"+ - "\u0404\u0005\u0001\u0000\u0000\u0404\u0405\u0005\u00a0\u0000\u0000\u0405"+ - "\u0406\u0003\u0084B\u0000\u0406\u0407\u0005\u0006\u0000\u0000\u0407\u0408"+ - "\u0005\u0002\u0000\u0000\u0408\u042c\u0001\u0000\u0000\u0000\u0409\u040a"+ - "\u0005\u0001\u0000\u0000\u040a\u040b\u0005\u00a4\u0000\u0000\u040b\u040c"+ - "\u0003\u0084B\u0000\u040c\u040d\u0005\u0006\u0000\u0000\u040d\u040e\u0005"+ - "\u0002\u0000\u0000\u040e\u042c\u0001\u0000\u0000\u0000\u040f\u0410\u0005"+ - "\u0001\u0000\u0000\u0410\u0411\u0005\u00a1\u0000\u0000\u0411\u0412\u0003"+ - "\u0086C\u0000\u0412\u0413\u0003\u0092I\u0000\u0413\u0414\u0005\u0002\u0000"+ - "\u0000\u0414\u042c\u0001\u0000\u0000\u0000\u0415\u0416\u0005\u0001\u0000"+ - "\u0000\u0416\u0417\u0005\u00a2\u0000\u0000\u0417\u0418\u0003\u0086C\u0000"+ - "\u0418\u0419\u0005\u0002\u0000\u0000\u0419\u042c\u0001\u0000\u0000\u0000"+ - "\u041a\u041b\u0005\u0001\u0000\u0000\u041b\u041c\u0005\u00a3\u0000\u0000"+ - "\u041c\u041d\u0003\u0086C\u0000\u041d\u041e\u0005\u0002\u0000\u0000\u041e"+ - "\u042c\u0001\u0000\u0000\u0000\u041f\u0420\u0005\u0001\u0000\u0000\u0420"+ - "\u0421\u0005\u00a4\u0000\u0000\u0421\u0422\u0003\u0086C\u0000\u0422\u0423"+ - "\u0005\u0006\u0000\u0000\u0423\u0424\u0005\u0002\u0000\u0000\u0424\u042c"+ - "\u0001\u0000\u0000\u0000\u0425\u0426\u0005\u0001\u0000\u0000\u0426\u0427"+ - "\u0005\u00a5\u0000\u0000\u0427\u0428\u0003\u0086C\u0000\u0428\u0429\u0005"+ - "\u0006\u0000\u0000\u0429\u042a\u0005\u0002\u0000\u0000\u042a\u042c\u0001"+ - "\u0000\u0000\u0000\u042b\u03f7\u0001\u0000\u0000\u0000\u042b\u03fd\u0001"+ - "\u0000\u0000\u0000\u042b\u0403\u0001\u0000\u0000\u0000\u042b\u0409\u0001"+ - "\u0000\u0000\u0000\u042b\u040f\u0001\u0000\u0000\u0000\u042b\u0415\u0001"+ - "\u0000\u0000\u0000\u042b\u041a\u0001\u0000\u0000\u0000\u042b\u041f\u0001"+ - "\u0000\u0000\u0000\u042b\u0425\u0001\u0000\u0000\u0000\u042c\u0089\u0001"+ - "\u0000\u0000\u0000\u042d\u043b\u0003\u0086C\u0000\u042e\u043b\u0003\u0088"+ - "D\u0000\u042f\u043b\u0003\u0084B\u0000\u0430\u0431\u0005\u0001\u0000\u0000"+ - "\u0431\u0432\u0005\u009b\u0000\u0000\u0432\u0434\u0003\u0002\u0001\u0000"+ - "\u0433\u0435\u0005\u00a8\u0000\u0000\u0434\u0433\u0001\u0000\u0000\u0000"+ - "\u0434\u0435\u0001\u0000\u0000\u0000\u0435\u0436\u0001\u0000\u0000\u0000"+ - "\u0436\u0437\u0005\u0002\u0000\u0000\u0437\u043b\u0001\u0000\u0000\u0000"+ - "\u0438\u043b\u0003\u008eG\u0000\u0439\u043b\u0003\u008cF\u0000\u043a\u042d"+ - "\u0001\u0000\u0000\u0000\u043a\u042e\u0001\u0000\u0000\u0000\u043a\u042f"+ - "\u0001\u0000\u0000\u0000\u043a\u0430\u0001\u0000\u0000\u0000\u043a\u0438"+ - "\u0001\u0000\u0000\u0000\u043a\u0439\u0001\u0000\u0000\u0000\u043b\u008b"+ - "\u0001\u0000\u0000\u0000\u043c\u043d\u0005\u0001\u0000\u0000\u043d\u043e"+ - "\u0005\u0095\u0000\u0000\u043e\u0440\u0005\u0099\u0000\u0000\u043f\u0441"+ - "\u0005\u00a8\u0000\u0000\u0440\u043f\u0001\u0000\u0000\u0000\u0440\u0441"+ - "\u0001\u0000\u0000\u0000\u0441\u0443\u0001\u0000\u0000\u0000\u0442\u0444"+ - "\u0005\u00a8\u0000\u0000\u0443\u0442\u0001\u0000\u0000\u0000\u0443\u0444"+ - "\u0001\u0000\u0000\u0000\u0444\u0445\u0001\u0000\u0000\u0000\u0445\u0446"+ - "\u0005\u0002\u0000\u0000\u0446\u008d\u0001\u0000\u0000\u0000\u0447\u0448"+ - "\u0005\u0001\u0000\u0000\u0448\u044a\u0005\u009a\u0000\u0000\u0449\u044b"+ - "\u0005\u00a8\u0000\u0000\u044a\u0449\u0001\u0000\u0000\u0000\u044a\u044b"+ - "\u0001\u0000\u0000\u0000\u044b\u044f\u0001\u0000\u0000\u0000\u044c\u044e"+ - "\u0003\u008aE\u0000\u044d\u044c\u0001\u0000\u0000\u0000\u044e\u0451\u0001"+ - "\u0000\u0000\u0000\u044f\u044d\u0001\u0000\u0000\u0000\u044f\u0450\u0001"+ - "\u0000\u0000\u0000\u0450\u0452\u0001\u0000\u0000\u0000\u0451\u044f\u0001"+ - "\u0000\u0000\u0000\u0452\u0468\u0005\u0002\u0000\u0000\u0453\u0454\u0005"+ - "\u0001\u0000\u0000\u0454\u0456\u0005\u00a6\u0000\u0000\u0455\u0457\u0005"+ - "\u00a8\u0000\u0000\u0456\u0455\u0001\u0000\u0000\u0000\u0456\u0457\u0001"+ - "\u0000\u0000\u0000\u0457\u0458\u0001\u0000\u0000\u0000\u0458\u0459\u0005"+ - "\u0006\u0000\u0000\u0459\u0468\u0005\u0002\u0000\u0000\u045a\u045b\u0005"+ - "\u0001\u0000\u0000\u045b\u045d\u0005\u00a7\u0000\u0000\u045c\u045e\u0005"+ - "\u00a8\u0000\u0000\u045d\u045c\u0001\u0000\u0000\u0000\u045d\u045e\u0001"+ - "\u0000\u0000\u0000\u045e\u045f\u0001\u0000\u0000\u0000\u045f\u0460\u0005"+ - "\u0006\u0000\u0000\u0460\u0468\u0005\u0002\u0000\u0000\u0461\u0462\u0005"+ - "\u0001\u0000\u0000\u0462\u0464\u0005\u00a7\u0000\u0000\u0463\u0465\u0005"+ - "\u00a8\u0000\u0000\u0464\u0463\u0001\u0000\u0000\u0000\u0464\u0465\u0001"+ - "\u0000\u0000\u0000\u0465\u0466\u0001\u0000\u0000\u0000\u0466\u0468\u0005"+ - "\u0002\u0000\u0000\u0467\u0447\u0001\u0000\u0000\u0000\u0467\u0453\u0001"+ - "\u0000\u0000\u0000\u0467\u045a\u0001\u0000\u0000\u0000\u0467\u0461\u0001"+ - "\u0000\u0000\u0000\u0468\u008f\u0001\u0000\u0000\u0000\u0469\u046a\u0005"+ - "\u0001\u0000\u0000\u046a\u046b\u0005\b\u0000\u0000\u046b\u046c\u0003\u001e"+ - "\u000f\u0000\u046c\u046d\u0005\u0002\u0000\u0000\u046d\u0091\u0001\u0000"+ - "\u0000\u0000\u046e\u0470\u0003\u0090H\u0000\u046f\u046e\u0001\u0000\u0000"+ - "\u0000\u0470\u0473\u0001\u0000\u0000\u0000\u0471\u046f\u0001\u0000\u0000"+ - "\u0000\u0471\u0472\u0001\u0000\u0000\u0000\u0472\u0093\u0001\u0000\u0000"+ - "\u0000\u0473\u0471\u0001\u0000\u0000\u0000\u0474\u0476\u0003\u008aE\u0000"+ - "\u0475\u0474\u0001\u0000\u0000\u0000\u0476\u0479\u0001\u0000\u0000\u0000"+ - "\u0477\u0475\u0001\u0000\u0000\u0000\u0477\u0478\u0001\u0000\u0000\u0000"+ - "\u0478\u047a\u0001\u0000\u0000\u0000\u0479\u0477\u0001\u0000\u0000\u0000"+ - "\u047a\u0483\u0005\u0000\u0000\u0001\u047b\u047d\u0003\u0080@\u0000\u047c"+ - "\u047b\u0001\u0000\u0000\u0000\u047d\u047e\u0001\u0000\u0000\u0000\u047e"+ - "\u047c\u0001\u0000\u0000\u0000\u047e\u047f\u0001\u0000\u0000\u0000\u047f"+ - "\u0480\u0001\u0000\u0000\u0000\u0480\u0481\u0005\u0000\u0000\u0001\u0481"+ - "\u0483\u0001\u0000\u0000\u0000\u0482\u0477\u0001\u0000\u0000\u0000\u0482"+ - "\u047c\u0001\u0000\u0000\u0000\u0483\u0095\u0001\u0000\u0000\u0000\u0484"+ - "\u0485\u0003\u0082A\u0000\u0485\u0486\u0005\u0000\u0000\u0001\u0486\u048f"+ - "\u0001\u0000\u0000\u0000\u0487\u0489\u0003\u0080@\u0000\u0488\u0487\u0001"+ - "\u0000\u0000\u0000\u0489\u048c\u0001\u0000\u0000\u0000\u048a\u0488\u0001"+ - "\u0000\u0000\u0000\u048a\u048b\u0001\u0000\u0000\u0000\u048b\u048d\u0001"+ - "\u0000\u0000\u0000\u048c\u048a\u0001\u0000\u0000\u0000\u048d\u048f\u0005"+ - "\u0000\u0000\u0001\u048e\u0484\u0001\u0000\u0000\u0000\u048e\u048a\u0001"+ - "\u0000\u0000\u0000\u048f\u0097\u0001\u0000\u0000\u0000|\u00ab\u00b2\u00b7"+ + "\u02a9\u0005\u008e\u0000\u0000\u02a9\u02aa\u0005\u0001\u0000\u0000\u02aa"+ + "\u02ab\u0003$\u0012\u0000\u02ab\u02ac\u0005\u0002\u0000\u0000\u02ac\u02b0"+ + "\u0005\u0085\u0000\u0000\u02ad\u02af\u0003 \u0010\u0000\u02ae\u02ad\u0001"+ + "\u0000\u0000\u0000\u02af\u02b2\u0001\u0000\u0000\u0000\u02b0\u02ae\u0001"+ + "\u0000\u0000\u0000\u02b0\u02b1\u0001\u0000\u0000\u0000\u02b1\u02b3\u0001"+ + "\u0000\u0000\u0000\u02b2\u02b0\u0001\u0000\u0000\u0000\u02b3\u02b4\u0005"+ + "\u0002\u0000\u0000\u02b4_\u0001\u0000\u0000\u0000\u02b5\u02b6\u0005\u0001"+ + "\u0000\u0000\u02b6\u02b8\u0005\u008c\u0000\u0000\u02b7\u02b9\u0003\"\u0011"+ + "\u0000\u02b8\u02b7\u0001\u0000\u0000\u0000\u02b8\u02b9\u0001\u0000\u0000"+ + "\u0000\u02b9\u02ba\u0001\u0000\u0000\u0000\u02ba\u02bb\u0003b1\u0000\u02bb"+ + "\u02bc\u0005\u0002\u0000\u0000\u02bca\u0001\u0000\u0000\u0000\u02bd\u02d0"+ + "\u0003\u0018\f\u0000\u02be\u02bf\u0003r9\u0000\u02bf\u02c0\u0003\u0018"+ + "\f\u0000\u02c0\u02d0\u0001\u0000\u0000\u0000\u02c1\u02c2\u0003x<\u0000"+ + "\u02c2\u02c3\u0003b1\u0000\u02c3\u02d0\u0001\u0000\u0000\u0000\u02c4\u02c5"+ + "\u0003\u0006\u0003\u0000\u02c5\u02c6\u0005\u0001\u0000\u0000\u02c6\u02ca"+ + "\u0005\u008e\u0000\u0000\u02c7\u02c9\u0003 \u0010\u0000\u02c8\u02c7\u0001"+ + "\u0000\u0000\u0000\u02c9\u02cc\u0001\u0000\u0000\u0000\u02ca\u02c8\u0001"+ + "\u0000\u0000\u0000\u02ca\u02cb\u0001\u0000\u0000\u0000\u02cb\u02cd\u0001"+ + "\u0000\u0000\u0000\u02cc\u02ca\u0001\u0000\u0000\u0000\u02cd\u02ce\u0005"+ + "\u0002\u0000\u0000\u02ce\u02d0\u0001\u0000\u0000\u0000\u02cf\u02bd\u0001"+ + "\u0000\u0000\u0000\u02cf\u02be\u0001\u0000\u0000\u0000\u02cf\u02c1\u0001"+ + "\u0000\u0000\u0000\u02cf\u02c4\u0001\u0000\u0000\u0000\u02d0c\u0001\u0000"+ + "\u0000\u0000\u02d1\u02d2\u0005\u0001\u0000\u0000\u02d2\u02d4\u0005\u008f"+ + "\u0000\u0000\u02d3\u02d5\u0003 \u0010\u0000\u02d4\u02d3\u0001\u0000\u0000"+ + "\u0000\u02d4\u02d5\u0001\u0000\u0000\u0000\u02d5\u02d6\u0001\u0000\u0000"+ + "\u0000\u02d6\u02d7\u0005\u0001\u0000\u0000\u02d7\u02d8\u0003$\u0012\u0000"+ + "\u02d8\u02dc\u0005\u0002\u0000\u0000\u02d9\u02db\u0005\u0006\u0000\u0000"+ + "\u02da\u02d9\u0001\u0000\u0000\u0000\u02db\u02de\u0001\u0000\u0000\u0000"+ + "\u02dc\u02da\u0001\u0000\u0000\u0000\u02dc\u02dd\u0001\u0000\u0000\u0000"+ + "\u02dd\u02df\u0001\u0000\u0000\u0000\u02de\u02dc\u0001\u0000\u0000\u0000"+ + "\u02df\u02e0\u0005\u0002\u0000\u0000\u02e0\u02f0\u0001\u0000\u0000\u0000"+ + "\u02e1\u02e2\u0005\u0001\u0000\u0000\u02e2\u02e4\u0005\u008f\u0000\u0000"+ + "\u02e3\u02e5\u0003 \u0010\u0000\u02e4\u02e3\u0001\u0000\u0000\u0000\u02e4"+ + "\u02e5\u0001\u0000\u0000\u0000\u02e5\u02e6\u0001\u0000\u0000\u0000\u02e6"+ + "\u02ea\u0003\\.\u0000\u02e7\u02e9\u0005\u0006\u0000\u0000\u02e8\u02e7"+ + "\u0001\u0000\u0000\u0000\u02e9\u02ec\u0001\u0000\u0000\u0000\u02ea\u02e8"+ + "\u0001\u0000\u0000\u0000\u02ea\u02eb\u0001\u0000\u0000\u0000\u02eb\u02ed"+ + "\u0001\u0000\u0000\u0000\u02ec\u02ea\u0001\u0000\u0000\u0000\u02ed\u02ee"+ + "\u0005\u0002\u0000\u0000\u02ee\u02f0\u0001\u0000\u0000\u0000\u02ef\u02d1"+ + "\u0001\u0000\u0000\u0000\u02ef\u02e1\u0001\u0000\u0000\u0000\u02f0e\u0001"+ + "\u0000\u0000\u0000\u02f1\u02f2\u0005\u0001\u0000\u0000\u02f2\u02f4\u0005"+ + "\u008d\u0000\u0000\u02f3\u02f5\u0003\"\u0011\u0000\u02f4\u02f3\u0001\u0000"+ + "\u0000\u0000\u02f4\u02f5\u0001\u0000\u0000\u0000\u02f5\u02f6\u0001\u0000"+ + "\u0000\u0000\u02f6\u02f7\u0003h4\u0000\u02f7\u02f8\u0005\u0002\u0000\u0000"+ + "\u02f8g\u0001\u0000\u0000\u0000\u02f9\u030a\u0003\u001a\r\u0000\u02fa"+ + "\u02fb\u0003r9\u0000\u02fb\u02fc\u0003\u001a\r\u0000\u02fc\u030a\u0001"+ + "\u0000\u0000\u0000\u02fd\u02fe\u0003x<\u0000\u02fe\u02ff\u0003h4\u0000"+ + "\u02ff\u030a\u0001\u0000\u0000\u0000\u0300\u0301\u0005\u0001\u0000\u0000"+ + "\u0301\u0305\u0005\u008f\u0000\u0000\u0302\u0304\u0005\u0006\u0000\u0000"+ + "\u0303\u0302\u0001\u0000\u0000\u0000\u0304\u0307\u0001\u0000\u0000\u0000"+ + "\u0305\u0303\u0001\u0000\u0000\u0000\u0305\u0306\u0001\u0000\u0000\u0000"+ + "\u0306\u0308\u0001\u0000\u0000\u0000\u0307\u0305\u0001\u0000\u0000\u0000"+ + "\u0308\u030a\u0005\u0002\u0000\u0000\u0309\u02f9\u0001\u0000\u0000\u0000"+ + "\u0309\u02fa\u0001\u0000\u0000\u0000\u0309\u02fd\u0001\u0000\u0000\u0000"+ + "\u0309\u0300\u0001\u0000\u0000\u0000\u030ai\u0001\u0000\u0000\u0000\u030b"+ + "\u030c\u0005\u0001\u0000\u0000\u030c\u030e\u0005\u008b\u0000\u0000\u030d"+ + "\u030f\u0003\"\u0011\u0000\u030e\u030d\u0001\u0000\u0000\u0000\u030e\u030f"+ + "\u0001\u0000\u0000\u0000\u030f\u0310\u0001\u0000\u0000\u0000\u0310\u0311"+ + "\u0003l6\u0000\u0311\u0312\u0005\u0002\u0000\u0000\u0312k\u0001\u0000"+ + "\u0000\u0000\u0313\u0314\u0003\u000e\u0007\u0000\u0314\u0315\u0003R)\u0000"+ + "\u0315\u031d\u0001\u0000\u0000\u0000\u0316\u0317\u0003r9\u0000\u0317\u0318"+ + "\u0003\u000e\u0007\u0000\u0318\u031d\u0001\u0000\u0000\u0000\u0319\u031a"+ + "\u0003x<\u0000\u031a\u031b\u0003l6\u0000\u031b\u031d\u0001\u0000\u0000"+ + "\u0000\u031c\u0313\u0001\u0000\u0000\u0000\u031c\u0316\u0001\u0000\u0000"+ + "\u0000\u031c\u0319\u0001\u0000\u0000\u0000\u031dm\u0001\u0000\u0000\u0000"+ + "\u031e\u031f\u0005\u0001\u0000\u0000\u031f\u0321\u0005\u0085\u0000\u0000"+ + "\u0320\u0322\u0003\"\u0011\u0000\u0321\u0320\u0001\u0000\u0000\u0000\u0321"+ + "\u0322\u0001\u0000\u0000\u0000\u0322\u0323\u0001\u0000\u0000\u0000\u0323"+ + "\u0324\u0003\u001c\u000e\u0000\u0324\u0325\u0005\u0002\u0000\u0000\u0325"+ + "\u0347\u0001\u0000\u0000\u0000\u0326\u0327\u0005\u0001\u0000\u0000\u0327"+ + "\u0329\u0005\u0085\u0000\u0000\u0328\u032a\u0003\"\u0011\u0000\u0329\u0328"+ + "\u0001\u0000\u0000\u0000\u0329\u032a\u0001\u0000\u0000\u0000\u032a\u032b"+ + "\u0001\u0000\u0000\u0000\u032b\u032c\u0003\u0016\u000b\u0000\u032c\u032d"+ + "\u0005\u0002\u0000\u0000\u032d\u0347\u0001\u0000\u0000\u0000\u032e\u032f"+ + "\u0005\u0001\u0000\u0000\u032f\u0331\u0005\u008c\u0000\u0000\u0330\u0332"+ + "\u0003\"\u0011\u0000\u0331\u0330\u0001\u0000\u0000\u0000\u0331\u0332\u0001"+ + "\u0000\u0000\u0000\u0332\u0333\u0001\u0000\u0000\u0000\u0333\u0334\u0003"+ + "\u0018\f\u0000\u0334\u0335\u0005\u0002\u0000\u0000\u0335\u0347\u0001\u0000"+ + "\u0000\u0000\u0336\u0337\u0005\u0001\u0000\u0000\u0337\u0339\u0005\u008d"+ + "\u0000\u0000\u0338\u033a\u0003\"\u0011\u0000\u0339\u0338\u0001\u0000\u0000"+ + "\u0000\u0339\u033a\u0001\u0000\u0000\u0000\u033a\u033b\u0001\u0000\u0000"+ + "\u0000\u033b\u033c\u0003\u001a\r\u0000\u033c\u033d\u0005\u0002\u0000\u0000"+ + "\u033d\u0347\u0001\u0000\u0000\u0000\u033e\u033f\u0005\u0001\u0000\u0000"+ + "\u033f\u0341\u0005\u008b\u0000\u0000\u0340\u0342\u0003\"\u0011\u0000\u0341"+ + "\u0340\u0001\u0000\u0000\u0000\u0341\u0342\u0001\u0000\u0000\u0000\u0342"+ + "\u0343\u0001\u0000\u0000\u0000\u0343\u0344\u0003\u000e\u0007\u0000\u0344"+ + "\u0345\u0005\u0002\u0000\u0000\u0345\u0347\u0001\u0000\u0000\u0000\u0346"+ + "\u031e\u0001\u0000\u0000\u0000\u0346\u0326\u0001\u0000\u0000\u0000\u0346"+ + "\u032e\u0001\u0000\u0000\u0000\u0346\u0336\u0001\u0000\u0000\u0000\u0346"+ + "\u033e\u0001\u0000\u0000\u0000\u0347o\u0001\u0000\u0000\u0000\u0348\u0349"+ + "\u0005\u0001\u0000\u0000\u0349\u034a\u0005\u0091\u0000\u0000\u034a\u034b"+ + "\u0003\u0002\u0001\u0000\u034b\u034c\u0003\u0002\u0001\u0000\u034c\u034d"+ + "\u0003n7\u0000\u034d\u034e\u0005\u0002\u0000\u0000\u034eq\u0001\u0000"+ + "\u0000\u0000\u034f\u0350\u0005\u0001\u0000\u0000\u0350\u0351\u0005\u0091"+ + "\u0000\u0000\u0351\u0352\u0003\u0002\u0001\u0000\u0352\u0353\u0003\u0002"+ + "\u0001\u0000\u0353\u0354\u0005\u0002\u0000\u0000\u0354s\u0001\u0000\u0000"+ + "\u0000\u0355\u0356\u0005\u0001\u0000\u0000\u0356\u0357\u0005\u0085\u0000"+ + "\u0000\u0357\u0358\u0003 \u0010\u0000\u0358\u0359\u0005\u0002\u0000\u0000"+ + "\u0359\u036a\u0001\u0000\u0000\u0000\u035a\u035b\u0005\u0001\u0000\u0000"+ + "\u035b\u035c\u0005\u008c\u0000\u0000\u035c\u035d\u0003 \u0010\u0000\u035d"+ + "\u035e\u0005\u0002\u0000\u0000\u035e\u036a\u0001\u0000\u0000\u0000\u035f"+ + "\u0360\u0005\u0001\u0000\u0000\u0360\u0361\u0005\u008d\u0000\u0000\u0361"+ + "\u0362\u0003 \u0010\u0000\u0362\u0363\u0005\u0002\u0000\u0000\u0363\u036a"+ + "\u0001\u0000\u0000\u0000\u0364\u0365\u0005\u0001\u0000\u0000\u0365\u0366"+ + "\u0005\u008b\u0000\u0000\u0366\u0367\u0003 \u0010\u0000\u0367\u0368\u0005"+ + "\u0002\u0000\u0000\u0368\u036a\u0001\u0000\u0000\u0000\u0369\u0355\u0001"+ + "\u0000\u0000\u0000\u0369\u035a\u0001\u0000\u0000\u0000\u0369\u035f\u0001"+ + "\u0000\u0000\u0000\u0369\u0364\u0001\u0000\u0000\u0000\u036au\u0001\u0000"+ + "\u0000\u0000\u036b\u036c\u0005\u0001\u0000\u0000\u036c\u036d\u0005\u0092"+ + "\u0000\u0000\u036d\u036e\u0003\u0002\u0001\u0000\u036e\u036f\u0003t:\u0000"+ + "\u036f\u0370\u0005\u0002\u0000\u0000\u0370w\u0001\u0000\u0000\u0000\u0371"+ + "\u0372\u0005\u0001\u0000\u0000\u0372\u0373\u0005\u0092\u0000\u0000\u0373"+ + "\u0374\u0003\u0002\u0001\u0000\u0374\u0375\u0005\u0002\u0000\u0000\u0375"+ + "y\u0001\u0000\u0000\u0000\u0376\u0377\u0005\u0001\u0000\u0000\u0377\u0379"+ + "\u0005\u0093\u0000\u0000\u0378\u037a\u0003\"\u0011\u0000\u0379\u0378\u0001"+ + "\u0000\u0000\u0000\u0379\u037a\u0001\u0000\u0000\u0000\u037a\u037b\u0001"+ + "\u0000\u0000\u0000\u037b\u037c\u0003\u001c\u000e\u0000\u037c\u037d\u0003"+ + "\u0016\u000b\u0000\u037d\u037e\u0005\u0002\u0000\u0000\u037e{\u0001\u0000"+ + "\u0000\u0000\u037f\u0380\u0005\u0001\u0000\u0000\u0380\u0382\u0005\u0084"+ + "\u0000\u0000\u0381\u0383\u0003\"\u0011\u0000\u0382\u0381\u0001\u0000\u0000"+ + "\u0000\u0382\u0383\u0001\u0000\u0000\u0000\u0383\u0384\u0001\u0000\u0000"+ + "\u0000\u0384\u0385\u0003\u0010\b\u0000\u0385\u0386\u0005\u0002\u0000\u0000"+ + "\u0386}\u0001\u0000\u0000\u0000\u0387\u0388\u0005\u0001\u0000\u0000\u0388"+ + "\u0389\u0005\u0087\u0000\u0000\u0389\u038a\u0003 \u0010\u0000\u038a\u038b"+ + "\u0005\u0002\u0000\u0000\u038b\u007f\u0001\u0000\u0000\u0000\u038c\u0398"+ + "\u0003|>\u0000\u038d\u0398\u0003j5\u0000\u038e\u0398\u0003`0\u0000\u038f"+ + "\u0398\u0003f3\u0000\u0390\u0398\u0003T*\u0000\u0391\u0398\u0003^/\u0000"+ + "\u0392\u0398\u0003d2\u0000\u0393\u0398\u0003~?\u0000\u0394\u0398\u0003"+ + "p8\u0000\u0395\u0398\u0003v;\u0000\u0396\u0398\u0003z=\u0000\u0397\u038c"+ + "\u0001\u0000\u0000\u0000\u0397\u038d\u0001\u0000\u0000\u0000\u0397\u038e"+ + "\u0001\u0000\u0000\u0000\u0397\u038f\u0001\u0000\u0000\u0000\u0397\u0390"+ + "\u0001\u0000\u0000\u0000\u0397\u0391\u0001\u0000\u0000\u0000\u0397\u0392"+ + "\u0001\u0000\u0000\u0000\u0397\u0393\u0001\u0000\u0000\u0000\u0397\u0394"+ + "\u0001\u0000\u0000\u0000\u0397\u0395\u0001\u0000\u0000\u0000\u0397\u0396"+ + "\u0001\u0000\u0000\u0000\u0398\u0081\u0001\u0000\u0000\u0000\u0399\u039a"+ + "\u0005\u0001\u0000\u0000\u039a\u039c\u0005\u0095\u0000\u0000\u039b\u039d"+ + "\u0005\u00a8\u0000\u0000\u039c\u039b\u0001\u0000\u0000\u0000\u039c\u039d"+ + "\u0001\u0000\u0000\u0000\u039d\u03a1\u0001\u0000\u0000\u0000\u039e\u03a0"+ + "\u0003\u0080@\u0000\u039f\u039e\u0001\u0000\u0000\u0000\u03a0\u03a3\u0001"+ + "\u0000\u0000\u0000\u03a1\u039f\u0001\u0000\u0000\u0000\u03a1\u03a2\u0001"+ + "\u0000\u0000\u0000\u03a2\u03a4\u0001\u0000\u0000\u0000\u03a3\u03a1\u0001"+ + "\u0000\u0000\u0000\u03a4\u03a5\u0005\u0002\u0000\u0000\u03a5\u0083\u0001"+ + "\u0000\u0000\u0000\u03a6\u03c3\u0003\u0082A\u0000\u03a7\u03a8\u0005\u0001"+ + "\u0000\u0000\u03a8\u03aa\u0005\u0095\u0000\u0000\u03a9\u03ab\u0005\u00a8"+ + "\u0000\u0000\u03aa\u03a9\u0001\u0000\u0000\u0000\u03aa\u03ab\u0001\u0000"+ + "\u0000\u0000\u03ab\u03ac\u0001\u0000\u0000\u0000\u03ac\u03b0\u0007\u0003"+ + "\u0000\u0000\u03ad\u03af\u0005\u0006\u0000\u0000\u03ae\u03ad\u0001\u0000"+ + "\u0000\u0000\u03af\u03b2\u0001\u0000\u0000\u0000\u03b0\u03ae\u0001\u0000"+ + "\u0000\u0000\u03b0\u03b1\u0001\u0000\u0000\u0000\u03b1\u03b3\u0001\u0000"+ + "\u0000\u0000\u03b2\u03b0\u0001\u0000\u0000\u0000\u03b3\u03c3\u0005\u0002"+ + "\u0000\u0000\u03b4\u03b5\u0005\u0001\u0000\u0000\u03b5\u03b6\u0005\u0095"+ + "\u0000\u0000\u03b6\u03b8\u0005\u0098\u0000\u0000\u03b7\u03b9\u0005\u00a8"+ + "\u0000\u0000\u03b8\u03b7\u0001\u0000\u0000\u0000\u03b8\u03b9\u0001\u0000"+ + "\u0000\u0000\u03b9\u03ba\u0001\u0000\u0000\u0000\u03ba\u03be\u0005\u0096"+ + "\u0000\u0000\u03bb\u03bd\u0005\u0006\u0000\u0000\u03bc\u03bb\u0001\u0000"+ + "\u0000\u0000\u03bd\u03c0\u0001\u0000\u0000\u0000\u03be\u03bc\u0001\u0000"+ + "\u0000\u0000\u03be\u03bf\u0001\u0000\u0000\u0000\u03bf\u03c1\u0001\u0000"+ + "\u0000\u0000\u03c0\u03be\u0001\u0000\u0000\u0000\u03c1\u03c3\u0005\u0002"+ + "\u0000\u0000\u03c2\u03a6\u0001\u0000\u0000\u0000\u03c2\u03a7\u0001\u0000"+ + "\u0000\u0000\u03c2\u03b4\u0001\u0000\u0000\u0000\u03c3\u0085\u0001\u0000"+ + "\u0000\u0000\u03c4\u03c5\u0005\u0001\u0000\u0000\u03c5\u03c7\u0005\u009c"+ + "\u0000\u0000\u03c6\u03c8\u0005\u00a8\u0000\u0000\u03c7\u03c6\u0001\u0000"+ + "\u0000\u0000\u03c7\u03c8\u0001\u0000\u0000\u0000\u03c8\u03c9\u0001\u0000"+ + "\u0000\u0000\u03c9\u03ca\u0003\u0002\u0001\u0000\u03ca\u03cb\u0003\u0092"+ + "I\u0000\u03cb\u03cc\u0005\u0002\u0000\u0000\u03cc\u03d6\u0001\u0000\u0000"+ + "\u0000\u03cd\u03ce\u0005\u0001\u0000\u0000\u03ce\u03d0\u0005\u009d\u0000"+ + "\u0000\u03cf\u03d1\u0005\u00a8\u0000\u0000\u03d0\u03cf\u0001\u0000\u0000"+ + "\u0000\u03d0\u03d1\u0001\u0000\u0000\u0000\u03d1\u03d2\u0001\u0000\u0000"+ + "\u0000\u03d2\u03d3\u0003\u0002\u0001\u0000\u03d3\u03d4\u0005\u0002\u0000"+ + "\u0000\u03d4\u03d6\u0001\u0000\u0000\u0000\u03d5\u03c4\u0001\u0000\u0000"+ + "\u0000\u03d5\u03cd\u0001\u0000\u0000\u0000\u03d6\u0087\u0001\u0000\u0000"+ + "\u0000\u03d7\u03d8\u0005\u0001\u0000\u0000\u03d8\u03d9\u0005\u009e\u0000"+ + "\u0000\u03d9\u03da\u0003\u0084B\u0000\u03da\u03db\u0005\u0006\u0000\u0000"+ + "\u03db\u03dc\u0005\u0002\u0000\u0000\u03dc\u040c\u0001\u0000\u0000\u0000"+ + "\u03dd\u03de\u0005\u0001\u0000\u0000\u03de\u03df\u0005\u009f\u0000\u0000"+ + "\u03df\u03e0\u0003\u0084B\u0000\u03e0\u03e1\u0005\u0006\u0000\u0000\u03e1"+ + "\u03e2\u0005\u0002\u0000\u0000\u03e2\u040c\u0001\u0000\u0000\u0000\u03e3"+ + "\u03e4\u0005\u0001\u0000\u0000\u03e4\u03e5\u0005\u00a0\u0000\u0000\u03e5"+ + "\u03e6\u0003\u0084B\u0000\u03e6\u03e7\u0005\u0006\u0000\u0000\u03e7\u03e8"+ + "\u0005\u0002\u0000\u0000\u03e8\u040c\u0001\u0000\u0000\u0000\u03e9\u03ea"+ + "\u0005\u0001\u0000\u0000\u03ea\u03eb\u0005\u00a4\u0000\u0000\u03eb\u03ec"+ + "\u0003\u0084B\u0000\u03ec\u03ed\u0005\u0006\u0000\u0000\u03ed\u03ee\u0005"+ + "\u0002\u0000\u0000\u03ee\u040c\u0001\u0000\u0000\u0000\u03ef\u03f0\u0005"+ + "\u0001\u0000\u0000\u03f0\u03f1\u0005\u00a1\u0000\u0000\u03f1\u03f2\u0003"+ + "\u0086C\u0000\u03f2\u03f3\u0003\u0092I\u0000\u03f3\u03f4\u0005\u0002\u0000"+ + "\u0000\u03f4\u040c\u0001\u0000\u0000\u0000\u03f5\u03f6\u0005\u0001\u0000"+ + "\u0000\u03f6\u03f7\u0005\u00a2\u0000\u0000\u03f7\u03f8\u0003\u0086C\u0000"+ + "\u03f8\u03f9\u0005\u0002\u0000\u0000\u03f9\u040c\u0001\u0000\u0000\u0000"+ + "\u03fa\u03fb\u0005\u0001\u0000\u0000\u03fb\u03fc\u0005\u00a3\u0000\u0000"+ + "\u03fc\u03fd\u0003\u0086C\u0000\u03fd\u03fe\u0005\u0002\u0000\u0000\u03fe"+ + "\u040c\u0001\u0000\u0000\u0000\u03ff\u0400\u0005\u0001\u0000\u0000\u0400"+ + "\u0401\u0005\u00a4\u0000\u0000\u0401\u0402\u0003\u0086C\u0000\u0402\u0403"+ + "\u0005\u0006\u0000\u0000\u0403\u0404\u0005\u0002\u0000\u0000\u0404\u040c"+ + "\u0001\u0000\u0000\u0000\u0405\u0406\u0005\u0001\u0000\u0000\u0406\u0407"+ + "\u0005\u00a5\u0000\u0000\u0407\u0408\u0003\u0086C\u0000\u0408\u0409\u0005"+ + "\u0006\u0000\u0000\u0409\u040a\u0005\u0002\u0000\u0000\u040a\u040c\u0001"+ + "\u0000\u0000\u0000\u040b\u03d7\u0001\u0000\u0000\u0000\u040b\u03dd\u0001"+ + "\u0000\u0000\u0000\u040b\u03e3\u0001\u0000\u0000\u0000\u040b\u03e9\u0001"+ + "\u0000\u0000\u0000\u040b\u03ef\u0001\u0000\u0000\u0000\u040b\u03f5\u0001"+ + "\u0000\u0000\u0000\u040b\u03fa\u0001\u0000\u0000\u0000\u040b\u03ff\u0001"+ + "\u0000\u0000\u0000\u040b\u0405\u0001\u0000\u0000\u0000\u040c\u0089\u0001"+ + "\u0000\u0000\u0000\u040d\u041b\u0003\u0086C\u0000\u040e\u041b\u0003\u0088"+ + "D\u0000\u040f\u041b\u0003\u0084B\u0000\u0410\u0411\u0005\u0001\u0000\u0000"+ + "\u0411\u0412\u0005\u009b\u0000\u0000\u0412\u0414\u0003\u0002\u0001\u0000"+ + "\u0413\u0415\u0005\u00a8\u0000\u0000\u0414\u0413\u0001\u0000\u0000\u0000"+ + "\u0414\u0415\u0001\u0000\u0000\u0000\u0415\u0416\u0001\u0000\u0000\u0000"+ + "\u0416\u0417\u0005\u0002\u0000\u0000\u0417\u041b\u0001\u0000\u0000\u0000"+ + "\u0418\u041b\u0003\u008eG\u0000\u0419\u041b\u0003\u008cF\u0000\u041a\u040d"+ + "\u0001\u0000\u0000\u0000\u041a\u040e\u0001\u0000\u0000\u0000\u041a\u040f"+ + "\u0001\u0000\u0000\u0000\u041a\u0410\u0001\u0000\u0000\u0000\u041a\u0418"+ + "\u0001\u0000\u0000\u0000\u041a\u0419\u0001\u0000\u0000\u0000\u041b\u008b"+ + "\u0001\u0000\u0000\u0000\u041c\u041d\u0005\u0001\u0000\u0000\u041d\u041e"+ + "\u0005\u0095\u0000\u0000\u041e\u0420\u0005\u0099\u0000\u0000\u041f\u0421"+ + "\u0005\u00a8\u0000\u0000\u0420\u041f\u0001\u0000\u0000\u0000\u0420\u0421"+ + "\u0001\u0000\u0000\u0000\u0421\u0423\u0001\u0000\u0000\u0000\u0422\u0424"+ + "\u0005\u00a8\u0000\u0000\u0423\u0422\u0001\u0000\u0000\u0000\u0423\u0424"+ + "\u0001\u0000\u0000\u0000\u0424\u0425\u0001\u0000\u0000\u0000\u0425\u0426"+ + "\u0005\u0002\u0000\u0000\u0426\u008d\u0001\u0000\u0000\u0000\u0427\u0428"+ + "\u0005\u0001\u0000\u0000\u0428\u042a\u0005\u009a\u0000\u0000\u0429\u042b"+ + "\u0005\u00a8\u0000\u0000\u042a\u0429\u0001\u0000\u0000\u0000\u042a\u042b"+ + "\u0001\u0000\u0000\u0000\u042b\u042f\u0001\u0000\u0000\u0000\u042c\u042e"+ + "\u0003\u008aE\u0000\u042d\u042c\u0001\u0000\u0000\u0000\u042e\u0431\u0001"+ + "\u0000\u0000\u0000\u042f\u042d\u0001\u0000\u0000\u0000\u042f\u0430\u0001"+ + "\u0000\u0000\u0000\u0430\u0432\u0001\u0000\u0000\u0000\u0431\u042f\u0001"+ + "\u0000\u0000\u0000\u0432\u0448\u0005\u0002\u0000\u0000\u0433\u0434\u0005"+ + "\u0001\u0000\u0000\u0434\u0436\u0005\u00a6\u0000\u0000\u0435\u0437\u0005"+ + "\u00a8\u0000\u0000\u0436\u0435\u0001\u0000\u0000\u0000\u0436\u0437\u0001"+ + "\u0000\u0000\u0000\u0437\u0438\u0001\u0000\u0000\u0000\u0438\u0439\u0005"+ + "\u0006\u0000\u0000\u0439\u0448\u0005\u0002\u0000\u0000\u043a\u043b\u0005"+ + "\u0001\u0000\u0000\u043b\u043d\u0005\u00a7\u0000\u0000\u043c\u043e\u0005"+ + "\u00a8\u0000\u0000\u043d\u043c\u0001\u0000\u0000\u0000\u043d\u043e\u0001"+ + "\u0000\u0000\u0000\u043e\u043f\u0001\u0000\u0000\u0000\u043f\u0440\u0005"+ + "\u0006\u0000\u0000\u0440\u0448\u0005\u0002\u0000\u0000\u0441\u0442\u0005"+ + "\u0001\u0000\u0000\u0442\u0444\u0005\u00a7\u0000\u0000\u0443\u0445\u0005"+ + "\u00a8\u0000\u0000\u0444\u0443\u0001\u0000\u0000\u0000\u0444\u0445\u0001"+ + "\u0000\u0000\u0000\u0445\u0446\u0001\u0000\u0000\u0000\u0446\u0448\u0005"+ + "\u0002\u0000\u0000\u0447\u0427\u0001\u0000\u0000\u0000\u0447\u0433\u0001"+ + "\u0000\u0000\u0000\u0447\u043a\u0001\u0000\u0000\u0000\u0447\u0441\u0001"+ + "\u0000\u0000\u0000\u0448\u008f\u0001\u0000\u0000\u0000\u0449\u044a\u0005"+ + "\u0001\u0000\u0000\u044a\u044b\u0005\b\u0000\u0000\u044b\u044c\u0003\u001e"+ + "\u000f\u0000\u044c\u044d\u0005\u0002\u0000\u0000\u044d\u0091\u0001\u0000"+ + "\u0000\u0000\u044e\u0450\u0003\u0090H\u0000\u044f\u044e\u0001\u0000\u0000"+ + "\u0000\u0450\u0453\u0001\u0000\u0000\u0000\u0451\u044f\u0001\u0000\u0000"+ + "\u0000\u0451\u0452\u0001\u0000\u0000\u0000\u0452\u0093\u0001\u0000\u0000"+ + "\u0000\u0453\u0451\u0001\u0000\u0000\u0000\u0454\u0456\u0003\u008aE\u0000"+ + "\u0455\u0454\u0001\u0000\u0000\u0000\u0456\u0459\u0001\u0000\u0000\u0000"+ + "\u0457\u0455\u0001\u0000\u0000\u0000\u0457\u0458\u0001\u0000\u0000\u0000"+ + "\u0458\u045a\u0001\u0000\u0000\u0000\u0459\u0457\u0001\u0000\u0000\u0000"+ + "\u045a\u0463\u0005\u0000\u0000\u0001\u045b\u045d\u0003\u0080@\u0000\u045c"+ + "\u045b\u0001\u0000\u0000\u0000\u045d\u045e\u0001\u0000\u0000\u0000\u045e"+ + "\u045c\u0001\u0000\u0000\u0000\u045e\u045f\u0001\u0000\u0000\u0000\u045f"+ + "\u0460\u0001\u0000\u0000\u0000\u0460\u0461\u0005\u0000\u0000\u0001\u0461"+ + "\u0463\u0001\u0000\u0000\u0000\u0462\u0457\u0001\u0000\u0000\u0000\u0462"+ + "\u045c\u0001\u0000\u0000\u0000\u0463\u0095\u0001\u0000\u0000\u0000\u0464"+ + "\u0465\u0003\u0082A\u0000\u0465\u0466\u0005\u0000\u0000\u0001\u0466\u046f"+ + "\u0001\u0000\u0000\u0000\u0467\u0469\u0003\u0080@\u0000\u0468\u0467\u0001"+ + "\u0000\u0000\u0000\u0469\u046c\u0001\u0000\u0000\u0000\u046a\u0468\u0001"+ + "\u0000\u0000\u0000\u046a\u046b\u0001\u0000\u0000\u0000\u046b\u046d\u0001"+ + "\u0000\u0000\u0000\u046c\u046a\u0001\u0000\u0000\u0000\u046d\u046f\u0005"+ + "\u0000\u0000\u0001\u046e\u0464\u0001\u0000\u0000\u0000\u046e\u046a\u0001"+ + "\u0000\u0000\u0000\u046f\u0097\u0001\u0000\u0000\u0000v\u00ab\u00b2\u00b7"+ "\u00bf\u00cb\u00d2\u00d8\u00dd\u00e5\u00eb\u00f3\u00f9\u010b\u0123\u0136"+ "\u0139\u013d\u0140\u0165\u016c\u0180\u0185\u018c\u0191\u0194\u019b\u01a1"+ "\u01a9\u01af\u01b7\u01bd\u01c7\u01cd\u01d4\u01d9\u01dd\u01e2\u01e6\u01eb"+ "\u01ee\u01f2\u01fa\u0201\u0207\u0214\u021d\u0222\u0227\u022d\u0238\u023a"+ "\u023d\u0246\u024c\u0256\u025c\u0262\u0268\u026c\u0273\u0279\u027e\u0285"+ - "\u028f\u0295\u029a\u02a5\u02aa\u02b2\u02ba\u02c0\u02c8\u02cf\u02d3\u02d8"+ - "\u02ea\u02ef\u02f4\u02fc\u0304\u030a\u030f\u0314\u0325\u0329\u032e\u033c"+ - "\u0341\u0349\u0351\u0359\u0361\u0366\u0389\u0399\u03a2\u03b7\u03bc\u03c1"+ - "\u03ca\u03d0\u03d8\u03de\u03e2\u03e7\u03f0\u03f5\u042b\u0434\u043a\u0440"+ - "\u0443\u044a\u044f\u0456\u045d\u0464\u0467\u0471\u0477\u047e\u0482\u048a"+ - "\u048e"; + "\u028f\u0295\u029a\u02a5\u02b0\u02b8\u02ca\u02cf\u02d4\u02dc\u02e4\u02ea"+ + "\u02ef\u02f4\u0305\u0309\u030e\u031c\u0321\u0329\u0331\u0339\u0341\u0346"+ + "\u0369\u0379\u0382\u0397\u039c\u03a1\u03aa\u03b0\u03b8\u03be\u03c2\u03c7"+ + "\u03d0\u03d5\u040b\u0414\u041a\u0420\u0423\u042a\u042f\u0436\u043d\u0444"+ + "\u0447\u0451\u0457\u045e\u0462\u046a\u046e"; public static final ATN _ATN = new ATNDeserializer().deserialize(_serializedATN.toCharArray()); static { diff --git a/src/main/scala/wasm/AST.scala b/src/main/scala/wasm/AST.scala index 274b2b508..2aad8052c 100644 --- a/src/main/scala/wasm/AST.scala +++ b/src/main/scala/wasm/AST.scala @@ -27,7 +27,7 @@ case class ImportFuncTy(name: Option[String], t: FuncType) extends ImportDesc case class ImportFuncTyUse(name: Option[String], u: Int) extends ImportDesc abstract class ElemList extends WIR -case class ElemListFunc(funcs: List[String]) extends ElemList +case class ElemListFunc(funcs: List[Int]) extends ElemList case class ElemListExpr(exprs: List[List[Instr]]) extends ElemList abstract class FuncField extends WIR diff --git a/src/main/scala/wasm/Parser.scala b/src/main/scala/wasm/Parser.scala index 0ce9fa94e..5f03b5b1d 100644 --- a/src/main/scala/wasm/Parser.scala +++ b/src/main/scala/wasm/Parser.scala @@ -170,6 +170,22 @@ class GSWasmVisitor extends WatParserBaseVisitor[WIR] { f } + override def visitElem(ctx: ElemContext): Elem = { + val offsetInstrs = List(visit(ctx.instr()).asInstanceOf[Instr]) + val funcs = ctx.idx().asScala.map(getVar(_)).map { id => + try id.toInt + catch { + case _: NumberFormatException => + if (fnMap.contains(id)) fnMap(id) + else { + System.err.println(s"[Parser] Warning: unresolved elem function reference: $id") + -1 + } + } + }.toList + Elem(None, offsetInstrs, ElemListFunc(funcs)) + } + override def visitSimport(ctx: SimportContext): WIR = { val module = ctx.name(0).getText.substring(1).dropRight(1) val name = ctx.name(1).getText.substring(1).dropRight(1) diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index ce00c3d77..c59d9fd26 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -128,6 +128,7 @@ trait StagedWasmEvaluator extends SAIOps { class MCont[A] type Cont[A] = (MCont[A]) => A type Trail[A] = List[Context => Rep[Cont[A]]] + trait Func // a cache storing the compiled code for each function, to reduce re-compilation val compileCache = new HashMap[Int, Rep[(MCont[Unit]) => Unit]] @@ -464,6 +465,11 @@ trait StagedWasmEvaluator extends SAIOps { case Return => trail.last(ctx)(mkont) case Call(f) => evalCall(rest, kont, mkont, trail, f, false) case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) + case CallIndirect(ty, table) => + Predef.assert(table == 0, "Currently we can only have one table!") + val functy = module.types(ty) + Predef.println(s"Table = ") + evalCallIndirect(rest, kont, mkont, trail, functy.asInstanceOf[FuncType]) case _ => val todo = "todo-op".reflectCtrlWith[Unit]() eval(rest, kont, mkont, trail) @@ -472,6 +478,51 @@ trait StagedWasmEvaluator extends SAIOps { def forwardKont: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => mk.enter()) + def readFuncTable(index: Rep[Int]): Rep[Func] = { + "read-func-table".reflectCtrlWith[Func](index) + } + + def invokeWithMCont(func: Rep[Func], mkont: Rep[MCont[Unit]]): Rep[Unit] = { + "invoke-func-with-mcont".reflectCtrlWith[Unit](func, mkont) + } + + def evalCallIndirect(rest: List[Instr], + kont: Context => Rep[Cont[Unit]], + mkont: Rep[MCont[Unit]], + trail: Trail[Unit], + functy: FuncType) + (implicit ctx: Context): Rep[Unit] = { + val (ty, newCtx) = ctx.pop() + val index = Stack.popC(ty) + val symIndex = Stack.popS(ty) + Predef.assert(ty == NumType(I32Type)) + val id = Counter.getId() + ExploreTree.fillWithCallIndirect(symIndex.s, id) + ExploreTree.moveCursor(index.toInt) + val func = readFuncTable(index.toInt) + invokeWithMCont(func, mkont) + } + + def evalFunc(ty: FuncType, body: List[Instr], funcIndex: Int, locals: List[ValueType]): Rep[(MCont[Unit]) => Unit] = { + if (compileCache.contains(funcIndex)) { + compileCache(funcIndex) + } else { + val func = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Entered the function at $funcIndex, stackSize =", Stack.size) + // the return instruction is also stack polymorphic + def retK(ctx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + val offset = ctx.stackTypes.size - ty.out.size + Stack.shiftC(offset, ty.out.size) + Stack.shiftS(offset, ty.out.size) + mk.enter() + }) + eval(body, retK _, mk, retK _::Nil)(Context(Nil, locals)) + }) + compileCache(funcIndex) = func + func + } + } def evalCall(rest: List[Instr], kont: Context => Rep[Cont[Unit]], @@ -485,25 +536,7 @@ trait StagedWasmEvaluator extends SAIOps { val locals = bodyLocals ++ ty.inps instrCost += locals.size * 2 - 1 addInstrCost() - val callee = - if (compileCache.contains(funcIndex)) { - compileCache(funcIndex) - } else { - val callee = topFun((mk: Rep[MCont[Unit]]) => { - info(s"Entered the function at $funcIndex, stackSize =", Stack.size) - // the return instruction is also stack polymorphic - def retK(ctx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) - val offset = ctx.stackTypes.size - ty.out.size - Stack.shiftC(offset, ty.out.size) - Stack.shiftS(offset, ty.out.size) - mk.enter() - }) - eval(body, retK _, mk, retK _::Nil)(Context(Nil, locals)) - }) - compileCache(funcIndex) = callee - callee - } + val callee = evalFunc(ty, body, funcIndex, locals) // Predef.println(s"[DEBUG] locals size: ${locals.size}") val newCtx = ctx.take(ty.inps.size) val argsC = Stack.takeC(ty.inps) @@ -703,6 +736,7 @@ trait StagedWasmEvaluator extends SAIOps { val (instrs, locals) = (funBody.body, funBody.locals) // resetStacks() // Don't manually reset the global states (like stack), manage them in the driver initGlobals(module.globals) + initTable(module) Frames.pushFrameC(locals) Frames.pushFrameS(locals) eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) @@ -883,6 +917,27 @@ trait StagedWasmEvaluator extends SAIOps { } } + def initTable(module: ModuleInstance): Rep[Unit] = { + val haltK: Rep[Unit] => Rep[Unit] = (_) => { } + val mkont: Rep[MCont[Unit]] = makeInitMCont(topFun(haltK)) + for (definition <- module.defs) { + definition match { + case Elem(_, offset, funcIndices) => + eval(offset, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, Nil)) + val offsetC = Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + Predef.println(s"funcIndices: $funcIndices") + for ((fidx, i) <- funcIndices.asInstanceOf[ElemListFunc].funcs.view.zipWithIndex) { + val FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) = module.funcs(fidx) + val locals = bodyLocals ++ ty.inps + val func = evalFunc(ty, body, fidx, locals) + "init-func-table".reflectCtrlWith[Unit](offsetC.i, i, func) + } + case _ => () + } + } + } + // call unreachable def unreachable(): Rep[Unit] = { "unreachable".reflectCtrlWith[Unit]() @@ -933,6 +988,10 @@ trait StagedWasmEvaluator extends SAIOps { "tree-fill-if-else".reflectCtrlWith[Unit](s, id) } + def fillWithCallIndirect(s: Rep[SymVal], id: Int): Rep[Unit] = { + "tree-fill-call-indirect".reflectCtrlWith[Unit](s, id) + } + def fillWithNotToExplore(): Rep[Unit] = { "tree-fill-not-to-explore".reflectCtrlWith[Unit]() } @@ -951,6 +1010,10 @@ trait StagedWasmEvaluator extends SAIOps { "tree-move-cursor-no-control".reflectCtrlWith[Unit](branch) } + def moveCursor(index: Rep[Int]): Rep[Unit] = { + "tree-move-cursor-call-indirect-index".reflectCtrlWith[Unit](index) + } + def print(): Rep[Unit] = { "tree-print".reflectCtrlWith[Unit]() } @@ -1529,6 +1592,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { else if (m.toString.endsWith("SymVal")) "SymVal" else if (m.toString.endsWith("Snapshot")) "Snapshot_t" else if (m.toString.endsWith("MCont[Unit]")) "MCont_t" + else if (m.toString.endsWith("Func")) "Func_t" else super.remap(m) } @@ -1747,6 +1811,16 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("prependCont("); shallow(kont); emit(", "); shallow(mkont); emit(")") case Node(_, "mcont-enter", List(mkont), _) => shallow(mkont); emit(".enter()") + case Node(_, "init-func-table", List(offset, i, func), _) => + emit("FuncTable.set("); shallow(offset); emit(", "); shallow(i); emit(", "); shallow(func); emit(")") + case Node(_, "tree-fill-call-indirect", List(s, id), _) => + emit("ExploreTree.fillCallIndirectNode("); shallow(s); emit(", "); emit(id.toString); emit(")") + case Node(_, "invoke-func-with-mcont", List(f, mkont), _) => + shallow(f); emit("("); shallow(mkont); emit(")") + case Node(_, "read-func-table", List(funcIndex), _) => + emit("FuncTable.read("); shallow(funcIndex); emit(")") + case Node(_, "tree-move-cursor-call-indirect-index", List(index), _) => + emit("ExploreTree.moveCursorIndirect("); shallow(index); emit(")") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 2e10bf72a..e2f0ea26b 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -190,6 +190,10 @@ class TestStagedConcolicEval extends FunSuite { testFileConcreteCpp("./benchmarks/wasm/f32_test.wat", Some("test_f32")) } + test("call-indirect-concrete") { + testFileConcreteCpp("./benchmarks/wasm/call_indirect_test.wat") + } + // test("diverge") { // testFileConcolicCpp("./benchmarks/wasm/diverge.wat", Some("main")) // } From 43e1c8e99616a01be1dbc3ea2ce2e6b80ee1f4d8 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 04:36:12 -0500 Subject: [PATCH 086/105] final call_indirect --- headers/wasm/concolic_driver.hpp | 2 - headers/wasm/concrete_rt.hpp | 26 +++++- headers/wasm/profile.hpp | 41 ++------- headers/wasm/smt_solver.hpp | 4 + headers/wasm/symbolic_rt.hpp | 37 +++++++- .../scala/wasm/StagedConcolicMiniWasm.scala | 86 +++++++++++-------- .../genwasym/TestStagedConcolicEval.scala | 2 +- 7 files changed, 119 insertions(+), 79 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index cb3a40c0c..29639e573 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -108,8 +108,6 @@ inline void ConcolicDriver::main_exploration_loop() { if (auto snapshot = dynamic_cast(node->node.get())) { assert(REUSE_SNAPSHOT); auto snap = snapshot->get_snapshot(); - std::cout << "Model \n" - << model << std::endl; snap.resume_execution_by_model(node, model); } else { auto timer = ManagedTimer(TimeProfileKind::INSTR); diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index f991fc58f..082a90d78 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -554,22 +554,28 @@ class Frames_t { std::monostate popFrame(std::int32_t size) { assert(size >= 0); count -= size; + current_base = old_frame_bases.back(); + old_frame_bases.pop_back(); return std::monostate{}; } Num get(std::int32_t index) { Profile.step(StepProfileKind::GET); - auto ret = stack_ptr[count - 1 - index]; + auto ret = stack_ptr[current_base + index]; return ret; } void set(std::int32_t index, Num num) { Profile.step(StepProfileKind::SET); - stack_ptr[count - 1 - index] = num; + stack_ptr[current_base + index] = num; } void pushFrame(std::int32_t size) { assert(size >= 0); + assert(count + size <= FRAME_SIZE); + + old_frame_bases.push_back(current_base); + current_base = count; count += size; // Zero-initialize the new stack frames. for (std::int32_t i = 0; i < size; ++i) { @@ -577,7 +583,19 @@ class Frames_t { } } - void reset() { count = 0; } + void extendFrame(std::int32_t size) { + assert(size >= 0); + count += size; + // Zero-initialize the new stack frames. + for (std::int32_t i = 0; i < size; ++i) { + stack_ptr[count - 1 - i] = Num(0); + } + } + + void reset() { + count = 0; + current_base = 0; + } size_t size() const { return count; } @@ -594,6 +612,8 @@ class Frames_t { private: int32_t count; Num *stack_ptr; + int32_t current_base; + std::vector old_frame_bases; }; static Frames_t Frames; diff --git a/headers/wasm/profile.hpp b/headers/wasm/profile.hpp index c32e2b518..7afd4416f 100644 --- a/headers/wasm/profile.hpp +++ b/headers/wasm/profile.hpp @@ -180,6 +180,10 @@ class Profile_t { time_count[static_cast(kind)] += time; } + void remove_instruction_time(TimeProfileKind kind, double time) { + time_count[static_cast(kind)] -= time; + } + int step_count; std::array(StepProfileKind::OperationCount)> op_count; @@ -191,50 +195,23 @@ class Profile_t { static Profile_t Profile; -class Timer { +class ManagedTimer { public: - Timer() = delete; - Timer(TimeProfileKind kind) : kind(kind) { - elapsed = std::chrono::duration::zero(); + ManagedTimer() = delete; + ManagedTimer(TimeProfileKind kind) : kind(kind) { start = std::chrono::high_resolution_clock::now(); } - ~Timer() { + ~ManagedTimer() { auto end = std::chrono::high_resolution_clock::now(); - elapsed += end - start; + std::chrono::duration elapsed = end - start; Profile.add_instruction_time(kind, elapsed.count()); } - void stop() { elapsed += std::chrono::high_resolution_clock::now() - start; } - void resume() { start = std::chrono::high_resolution_clock::now(); } private: - std::chrono::duration elapsed; TimeProfileKind kind; std::chrono::high_resolution_clock::time_point start; }; -static std::vector TimerStack = []() { - std::vector v; - v.reserve(3); // initial capacity - return v; -}(); - -class ManagedTimer { -public: - ManagedTimer() = delete; - ManagedTimer(TimeProfileKind kind) { - if (TimerStack.size() > 0) { - TimerStack.back().stop(); - } - TimerStack.emplace_back(kind); - } - ~ManagedTimer() { - TimerStack.pop_back(); - if (TimerStack.size() > 0) { - TimerStack.back().resume(); - } - } -}; - struct CostManager_t { int instr_cost; diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index a34ab6d3e..8346d7f5a 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -180,7 +180,11 @@ inline EvalRes eval_sym_expr_by_model(const SymVal &sym, z3::model &model) { inline std::monostate GENSYM_SYM_ASSERT(SymVal &sym_cond) { std::vector conds = ExploreTree.collect_current_path_conds(); conds.push_back(sym_cond.negate()); + auto start = std::chrono::steady_clock::now(); auto result = solver.solve(conds); + auto end = std::chrono::steady_clock::now(); + auto time_need_to_be_removed = end - start; + Profile.remove_instruction_time(TimeProfileKind::INSTR, time_need_to_be_removed.count()); if (result.has_value()) { std::cout << "Symbolic assertion failed" << std::endl; throw std::runtime_error("Symbolic assertion failed"); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 50364ec22..814af51d2 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -355,37 +355,59 @@ class SymFrames_t { void pushFrame(int size) { // Push a new frame with the given size #ifdef USE_IMM + old_frame_bases.push_back(current_base); + current_base = stack.size(); for (int i = 0; i < size; ++i) { stack.push_back(SymVal()); } #else + old_frame_bases.push_back(current_base); + current_base = stack.size(); stack.resize(size + stack.size()); #endif } + + void extendFrame(int size) { + // Extend the current frame with the given size +#ifdef USE_IMM + for (int i = 0; i < size; ++i) { + stack.push_back(SymVal()); + } +#else + stack.resize(size + stack.size()); +#endif + } + std::monostate popFrame(int size) { // Pop the frame of the given size #ifdef USE_IMM stack.take(stack.size() - size); + current_base = old_frame_bases.end()[-1]; + old_frame_bases.take(old_frame_bases.size() - 1); #else stack.resize(stack.size() - size); + current_base = old_frame_bases.back(); + old_frame_bases.pop_back(); #endif return std::monostate(); } SymVal get(int index) { // Get the symbolic value at the given frame index - auto res = stack[stack.size() - 1 - index]; + assert(index >= 0 && index < size() - current_base); + auto res = stack[current_base + index]; return res; } void set(int index, SymVal val) { // Set the symbolic value at the given index assert(val.symptr != nullptr); + assert(index >= 0 && index < size() - current_base); #ifdef USE_IMM - stack.set(stack.size() - 1 - index, val); + stack.set(current_base + index, val); #else - stack[stack.size() - 1 - index] = val; + stack[current_base + index] = val; #endif } @@ -394,8 +416,12 @@ class SymFrames_t { #ifdef USE_IMM stack = immer::vector_transient(); + old_frame_bases = immer::vector_transient(); + current_base = 0; #else stack.clear(); + old_frame_bases.clear(); + current_base = 0; #endif } @@ -414,8 +440,12 @@ class SymFrames_t { private: #ifdef USE_IMM immer::vector_transient stack; + immer::vector_transient old_frame_bases; + int32_t current_base = 0; #else std::vector stack; + std::vector old_frame_bases; + int32_t current_base = 0; #endif }; @@ -897,7 +927,6 @@ inline std::monostate NodeBox::fillFailedNode() { if (this->isUnexplored()) { node = std::make_unique(); } else { - std::cout << "Fill Failed Node" << node->to_string() << std::endl; assert(dynamic_cast(node.get()) != nullptr); } return std::monostate(); diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index c59d9fd26..6ac2a83a1 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -463,8 +463,8 @@ trait StagedWasmEvaluator extends SAIOps { } aux(labels, 0, mkont) case Return => trail.last(ctx)(mkont) - case Call(f) => evalCall(rest, kont, mkont, trail, f, false) - case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f, true) + case Call(f) => evalCall(rest, kont, mkont, trail, f) + case ReturnCall(f) => evalCall(rest, kont, mkont, trail, f) case CallIndirect(ty, table) => Predef.assert(table == 0, "Currently we can only have one table!") val functy = module.types(ty) @@ -500,10 +500,22 @@ trait StagedWasmEvaluator extends SAIOps { ExploreTree.fillWithCallIndirect(symIndex.s, id) ExploreTree.moveCursor(index.toInt) val func = readFuncTable(index.toInt) - invokeWithMCont(func, mkont) + val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Returned from call_indirect, stackSize =", Stack.size) + eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = functy.out.reverse ++ newCtx.stackTypes.drop(functy.inps.size))) + }) + val newMKont: Rep[MCont[Unit]] = mkont.prependCont(restK) + + val argsC = Stack.takeC(functy.inps) + val argsS = Stack.takeS(functy.inps) + Frames.pushFrameC(functy.inps) + Frames.pushFrameS(functy.inps) + Frames.putAllC(argsC) + Frames.putAllS(argsS) + invokeWithMCont(func, newMKont) } - def evalFunc(ty: FuncType, body: List[Instr], funcIndex: Int, locals: List[ValueType]): Rep[(MCont[Unit]) => Unit] = { + def evalFunc(ty: FuncType, body: List[Instr], funcIndex: Int, inps: List[ValueType], locals: List[ValueType]): Rep[(MCont[Unit]) => Unit] = { if (compileCache.contains(funcIndex)) { compileCache(funcIndex) } else { @@ -515,9 +527,13 @@ trait StagedWasmEvaluator extends SAIOps { val offset = ctx.stackTypes.size - ty.out.size Stack.shiftC(offset, ty.out.size) Stack.shiftS(offset, ty.out.size) + Frames.popFrameC(inps.size + locals.size) + Frames.popFrameS(inps.size + locals.size) mk.enter() }) - eval(body, retK _, mk, retK _::Nil)(Context(Nil, locals)) + Frames.extendFrameC(locals.size) + Frames.extendFrameS(locals.size) + eval(body, retK _, mk, retK _::Nil)(Context(Nil, inps ++ locals)) }) compileCache(funcIndex) = func func @@ -528,44 +544,29 @@ trait StagedWasmEvaluator extends SAIOps { kont: Context => Rep[Cont[Unit]], mkont: Rep[MCont[Unit]], trail: Trail[Unit], - funcIndex: Int, - isTail: Boolean) + funcIndex: Int) (implicit ctx: Context): Rep[Unit] = { module.funcs(funcIndex) match { case FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) => - val locals = bodyLocals ++ ty.inps - instrCost += locals.size * 2 - 1 + instrCost += (ty.inps ++ bodyLocals).size * 2 - 1 addInstrCost() - val callee = evalFunc(ty, body, funcIndex, locals) + val callee = evalFunc(ty, body, funcIndex, ty.inps, bodyLocals) // Predef.println(s"[DEBUG] locals size: ${locals.size}") val newCtx = ctx.take(ty.inps.size) val argsC = Stack.takeC(ty.inps) val argsS = Stack.takeS(ty.inps) - if (isTail) { - // when tail call, return to the caller's return continuation - Frames.popFrameC(ctx.frameTypes.size) - Frames.popFrameS(ctx.frameTypes.size) - Frames.pushFrameC(locals) - Frames.pushFrameS(locals) - Frames.putAllC(argsC) - Frames.putAllS(argsS) - callee(mkont) - } else { - // We make a new trail by `restK`, since function creates a new block to escape - // (more or less like `return`) - val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) - Frames.popFrameC(locals.size) - Frames.popFrameS(locals.size) - eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) - }) - val newMKont: Rep[MCont[Unit]] = mkont.prependCont(restK) - Frames.pushFrameC(locals) - Frames.pushFrameS(locals) - Frames.putAllC(argsC) - Frames.putAllS(argsS) - callee(newMKont) - } + // We make a new trail by `restK`, since function creates a new block to escape + // (more or less like `return`) + val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { + info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) + }) + val newMKont: Rep[MCont[Unit]] = mkont.prependCont(restK) + Frames.pushFrameC(ty.inps) + Frames.pushFrameS(ty.inps) + Frames.putAllC(argsC) + Frames.putAllS(argsS) + callee(newMKont) case Import("console", "log", _) | Import("spectest", "print_i32", _) => //println(s"[DEBUG] current stack: $stack") @@ -852,12 +853,20 @@ trait StagedWasmEvaluator extends SAIOps { "frame-push".reflectCtrlWith[Unit](size) } + def extendFrameC(size: Int): Rep[Unit] = { + if (size > 0) "frame-extend".reflectCtrlWith[Unit](size) + } + def pushFrameS(locals: List[ValueType]): Rep[Unit] = { // Predef.println(s"[DEBUG] push frame: $locals") val size = locals.size "sym-frame-push".reflectCtrlWith[Unit](size) } + def extendFrameS(size: Int): Rep[Unit] = { + if (size > 0) "sym-frame-extend".reflectCtrlWith[Unit](size) + } + def popFrameC(size: Int): Rep[Unit] = { "frame-pop".reflectCtrlWith[Unit](size) } @@ -929,8 +938,7 @@ trait StagedWasmEvaluator extends SAIOps { Predef.println(s"funcIndices: $funcIndices") for ((fidx, i) <- funcIndices.asInstanceOf[ElemListFunc].funcs.view.zipWithIndex) { val FuncDef(_, FuncBodyDef(ty, _, bodyLocals, body)) = module.funcs(fidx) - val locals = bodyLocals ++ ty.inps - val func = evalFunc(ty, body, fidx, locals) + val func = evalFunc(ty, body, fidx, ty.inps, bodyLocals) "init-func-table".reflectCtrlWith[Unit](offsetC.i, i, func) } case _ => () @@ -1653,6 +1661,10 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("Stack.pop()") case Node(_, "sym-stack-pop", _, _) => emit("SymStack.pop()") + case Node(_, "frame-extend", List(i), _) => + emit("Frames.extendFrame("); shallow(i); emit(")") + case Node(_, "sym-frame-extend", List(i), _) => + emit("SymFrames.extendFrame("); shallow(i); emit(")") case Node(_, "control-make", List(k, mk), _) => emit("makeControl("); shallow(k); emit(", "); shallow(mk); emit(")") case Node(_, "frame-pop", List(i), _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index e2f0ea26b..53ed775e8 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -191,7 +191,7 @@ class TestStagedConcolicEval extends FunSuite { } test("call-indirect-concrete") { - testFileConcreteCpp("./benchmarks/wasm/call_indirect_test.wat") + testFileConcreteCpp("./benchmarks/wasm/call_indirect_test.wat", expect=Some(List(42))) } // test("diverge") { From 556f478cbb0ee2b52f53d8cf79238edf978629e5 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 06:13:52 -0500 Subject: [PATCH 087/105] misc --- benchmarks/pldi2026/btree/run.py | 7 ++++--- headers/wasm/concrete_rt.hpp | 10 ++++++++++ headers/wasm/output_report.hpp | 12 ++++-------- headers/wasm/smt_solver.hpp | 3 ++- headers/wasm/symbolic_rt.hpp | 6 +++++- 5 files changed, 25 insertions(+), 13 deletions(-) diff --git a/benchmarks/pldi2026/btree/run.py b/benchmarks/pldi2026/btree/run.py index 8f492488d..d816e11b1 100644 --- a/benchmarks/pldi2026/btree/run.py +++ b/benchmarks/pldi2026/btree/run.py @@ -40,12 +40,13 @@ def run_all(targets: list[Path], action): else: output_path = "NoConfig" + f"/{file_name}.output" - if Path(output_path).exists(): - print(f"Output path {output_path} already exists, skipping...") + num = len(list(Path(output_path).glob("*.json"))) if Path(output_path).exists() else 0 + if num >= 5: + print(f"Skip {file_name} since it already has {num} reports.") continue if action == "run": env = os.environ.copy() - env.update({"OUTPUT_DIR": output_path}) + env.update({"OUTPUT_FILE": output_path + f"/report_{num}.json"}) print("Now executing: " + str(file_path)) proc = subprocess.Popen( diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 082a90d78..fbf0b575e 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -609,6 +609,16 @@ class Frames_t { count = new_size; } + void resize_old_frames_size(int32_t new_size) { + assert(new_size >= 0); + old_frame_bases.resize(new_size); + } + + void set_old_frame_base(int32_t index, int32_t value) { + assert(index >= 0 && index < old_frame_bases.size()); + old_frame_bases[index] = value; + } + private: int32_t count; Num *stack_ptr; diff --git a/headers/wasm/output_report.hpp b/headers/wasm/output_report.hpp index a1a08f0b7..ef8de2a0e 100644 --- a/headers/wasm/output_report.hpp +++ b/headers/wasm/output_report.hpp @@ -8,17 +8,13 @@ inline void dump_all_summary_json(const Profile_t &profile, const OverallResult &overall) { - // use environment variable OUTPUT_DIR to config particular output directory - // use environment variable OUTPUT_DIR to config particular output directory - const char *output_dir = std::getenv("OUTPUT_DIR"); - if (output_dir == nullptr) { + // use environment variable OUTPUT_FILE to config particular output profiling file + const char *output_file = std::getenv("OUTPUT_FILE"); + if (output_file == nullptr) { return; } - std::filesystem::path outdir(output_dir); - - std::filesystem::path report_path = - outdir / std::filesystem::path("concolic_execution_report.json"); + std::filesystem::path report_path(output_file); auto parent = report_path.parent_path(); if (!parent.empty()) { diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 8346d7f5a..c68512692 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -183,7 +183,8 @@ inline std::monostate GENSYM_SYM_ASSERT(SymVal &sym_cond) { auto start = std::chrono::steady_clock::now(); auto result = solver.solve(conds); auto end = std::chrono::steady_clock::now(); - auto time_need_to_be_removed = end - start; + auto time_need_to_be_removed = std::chrono::duration(end - start); + std::cout << "Time taken for symbolic assertion: " << time_need_to_be_removed.count() << " seconds" << std::endl; Profile.remove_instruction_time(TimeProfileKind::INSTR, time_need_to_be_removed.count()); if (result.has_value()) { std::cout << "Symbolic assertion failed" << std::endl; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 814af51d2..5e009f6f7 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -437,7 +437,6 @@ class SymFrames_t { return cost; } -private: #ifdef USE_IMM immer::vector_transient stack; immer::vector_transient old_frame_bases; @@ -1563,6 +1562,11 @@ static void resume_conc_frames_by_model(const SymFrames_t &sym_frame, auto conc = res.value; frames.set_from_front(i, conc); } + frames.resize_old_frames_size(sym_frame.old_frame_bases.size()); + for (size_t i = 0; i < sym_frame.old_frame_bases.size(); ++i) { + auto base = sym_frame.old_frame_bases[i]; + frames.set_old_frame_base(i, base); + } } static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, From a841ee5173dbfcb446379638d380ad88f245fd9e Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 06:48:04 -0500 Subject: [PATCH 088/105] up --- headers/wasm/concrete_rt.hpp | 1 - 1 file changed, 1 deletion(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index fbf0b575e..901fb438a 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -619,7 +619,6 @@ class Frames_t { old_frame_bases[index] = value; } -private: int32_t count; Num *stack_ptr; int32_t current_base; From 9a1088b9db0ebb20869cbf9c17994490e1eb217a Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 10:49:59 -0500 Subject: [PATCH 089/105] fix --- headers/wasm/concolic_driver.hpp | 1 + headers/wasm/concrete_rt.hpp | 30 ++++++++----------- headers/wasm/smt_solver.hpp | 1 - headers/wasm/symbolic_rt.hpp | 7 +++-- .../scala/wasm/StagedConcolicMiniWasm.scala | 2 +- 5 files changed, 20 insertions(+), 21 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index 29639e573..e26d6dbd2 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -98,6 +98,7 @@ inline void ConcolicDriver::main_exploration_loop() { } auto &new_env = result.value().first; auto &model = result.value().second; + std::cout << "Get from model..." << std::endl << model << std::endl; // update global symbolic environment from SMT solved model SymEnv.update(std::move(new_env)); diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 901fb438a..753b3d63c 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -539,7 +539,7 @@ class Stack_t { }; static Stack_t Stack; -const int FRAME_SIZE = 1024; +const int FRAME_SIZE = 1024 * 8; class Frames_t { public: @@ -553,6 +553,7 @@ class Frames_t { std::monostate popFrame(std::int32_t size) { assert(size >= 0); + assert(size == count - current_base); count -= size; current_base = old_frame_bases.back(); old_frame_bases.pop_back(); @@ -637,7 +638,6 @@ static std::monostate unreachable() { throw std::runtime_error("Unreachable code reached"); } -static const int PRE_ALLOC_PAGES = 20; static int32_t pagesize = 65536; static int32_t page_count = 0; @@ -646,17 +646,12 @@ struct Memory_t { std::vector memory; int init_page_count; int page_count; - int allocated_pages; Memory_t(int32_t init_page_count) - : memory(PRE_ALLOC_PAGES * pagesize), init_page_count(init_page_count), - page_count(init_page_count), allocated_pages(PRE_ALLOC_PAGES) {} + : memory(pagesize), init_page_count(init_page_count), + page_count(init_page_count) {} int32_t loadInt(int32_t base, int32_t offset) { -#ifdef DEBUG - std::cout << "[Debug] loading int from memory at address: " - << (base + offset) << std::endl; -#endif // just load a 4-byte integer from memory of the vector int32_t addr = base + offset; if (!(addr + 3 < memory.size())) { @@ -667,6 +662,11 @@ struct Memory_t { for (int i = 0; i < 4; ++i) { result |= static_cast(memory[addr + i]) << (8 * i); } +#ifdef DEBUG + std::cout << "[Debug] loading int from memory at address: " + << (base + offset) << std::endl; + std::cout << "[Debug] loaded int value " << result << " from " << addr << std::endl; +#endif return result; } @@ -684,6 +684,7 @@ struct Memory_t { memory[addr + i] = static_cast((value >> (8 * i)) & 0xFF); // Optionally, update memory[addr + i].second (SymVal) if needed } + std::cout << "[Debug] stored int value " << value << " to " << addr << std::endl; return std::monostate{}; } @@ -701,15 +702,11 @@ struct Memory_t { return page_count * pagesize; } - if (page_count + delta < allocated_pages) { - page_count += delta; - return page_count * pagesize; - } - try { - assert(false && "Use pre-allocated memory, should not reach here"); memory.resize(memory.size() + delta * pagesize); - auto old_page_count = page_count; + for (int i = 0; i < delta * pagesize; ++i) { + memory[page_count * pagesize + i] = 0; + } page_count += delta; return memory.size(); } catch (const std::bad_alloc &e) { @@ -719,7 +716,6 @@ struct Memory_t { void reset() { page_count = init_page_count; - allocated_pages = PRE_ALLOC_PAGES; for (int i = 0; i < memory.size() && i < page_count * pagesize; ++i) { memory[i] = 0; } diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index c68512692..8e0de42a0 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -184,7 +184,6 @@ inline std::monostate GENSYM_SYM_ASSERT(SymVal &sym_cond) { auto result = solver.solve(conds); auto end = std::chrono::steady_clock::now(); auto time_need_to_be_removed = std::chrono::duration(end - start); - std::cout << "Time taken for symbolic assertion: " << time_need_to_be_removed.count() << " seconds" << std::endl; Profile.remove_instruction_time(TimeProfileKind::INSTR, time_need_to_be_removed.count()); if (result.has_value()) { std::cout << "Symbolic assertion failed" << std::endl; diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 5e009f6f7..e696d7656 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -382,6 +382,7 @@ class SymFrames_t { // Pop the frame of the given size #ifdef USE_IMM + assert(size == stack.size() - current_base); stack.take(stack.size() - size); current_base = old_frame_bases.end()[-1]; old_frame_bases.take(old_frame_bases.size() - 1); @@ -914,7 +915,7 @@ inline std::monostate NodeBox::fillNotToExploreNode() { } inline std::monostate NodeBox::fillFinishedNode() { - if (this->isUnexplored()) { + if (this->isUnexplored()) { node = std::make_unique(); } else { assert(dynamic_cast(node.get()) != nullptr); @@ -1372,7 +1373,8 @@ static std::monostate reset_stacks() { return std::monostate{}; } -inline void NodeBox::reach_here(std::function entrypoint) { +[[deprecated]] inline void +NodeBox::reach_here(std::function entrypoint) { // reach the node of exploration tree with given input (symbolic environment) if (auto snapshot = dynamic_cast(node.get())) { assert(REUSE_SNAPSHOT); @@ -1567,6 +1569,7 @@ static void resume_conc_frames_by_model(const SymFrames_t &sym_frame, auto base = sym_frame.old_frame_bases[i]; frames.set_old_frame_base(i, base); } + frames.current_base = sym_frame.current_base; } static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 6ac2a83a1..0b24dfde0 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -523,7 +523,7 @@ trait StagedWasmEvaluator extends SAIOps { info(s"Entered the function at $funcIndex, stackSize =", Stack.size) // the return instruction is also stack polymorphic def retK(ctx: Context): Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { - info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + info(s"Return from the function at $funcIndex, stackSize =", Stack.size) val offset = ctx.stackTypes.size - ty.out.size Stack.shiftC(offset, ty.out.size) Stack.shiftS(offset, ty.out.size) From 2fdc953635d43b6d06f757cc00295cccff398f1a Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:04:07 -0500 Subject: [PATCH 090/105] up btree for wasp --- benchmarks/pldi2026/wasp_btree/2o1u.wast | 3655 ++++++++++++++++++ benchmarks/pldi2026/wasp_btree/2o2u.wast | 3694 ++++++++++++++++++ benchmarks/pldi2026/wasp_btree/2o3u.wast | 3740 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/3o1u.wast | 3698 ++++++++++++++++++ benchmarks/pldi2026/wasp_btree/3o2u.wast | 3744 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/3o3u.wast | 3795 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/4o1u.wast | 3747 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/4o2u.wast | 3798 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/4o3u.wast | 3854 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/5o1u.wast | 3801 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/5o2u.wast | 3858 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/5o3u.wast | 3915 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/6o1u.wast | 3861 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/6o2u.wast | 3922 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/6o3u.wast | 3987 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/7o1u.wast | 3926 +++++++++++++++++++ benchmarks/pldi2026/wasp_btree/7o2u.wast | 3992 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/7o3u.wast | 4065 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/8o1u.wast | 3996 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/8o2u.wast | 4059 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/9o1u.wast | 4072 ++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/9o2u.wast | 4147 +++++++++++++++++++++ benchmarks/pldi2026/wasp_btree/BTree.wast | 4073 ++++++++++++++++++++ 23 files changed, 89399 insertions(+) create mode 100644 benchmarks/pldi2026/wasp_btree/2o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/2o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/2o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/3o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/3o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/3o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/4o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/4o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/4o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/5o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/5o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/5o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/6o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/6o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/6o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/7o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/7o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/7o3u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/8o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/8o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/9o1u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/9o2u.wast create mode 100644 benchmarks/pldi2026/wasp_btree/BTree.wast diff --git a/benchmarks/pldi2026/wasp_btree/2o1u.wast b/benchmarks/pldi2026/wasp_btree/2o1u.wast new file mode 100644 index 000000000..b9384f568 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/2o1u.wast @@ -0,0 +1,3655 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (print_stack) + (i32.const -1) + (i32.eq) + (print_stack) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (print_stack) + (i32.const -1) + (i32.eq) + (print_stack) + + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00")) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/2o2u.wast b/benchmarks/pldi2026/wasp_btree/2o2u.wast new file mode 100644 index 000000000..384e4feee --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/2o2u.wast @@ -0,0 +1,3694 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + ;; i + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00i\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/2o3u.wast b/benchmarks/pldi2026/wasp_btree/2o3u.wast new file mode 100644 index 000000000..090f36e0f --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/2o3u.wast @@ -0,0 +1,3740 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 2 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;; logical order: a>b + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1028) + (i32.symbolic) + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + ;; i + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/3o1u.wast b/benchmarks/pldi2026/wasp_btree/3o1u.wast new file mode 100644 index 000000000..ef2c9309a --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/3o1u.wast @@ -0,0 +1,3698 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/3o2u.wast b/benchmarks/pldi2026/wasp_btree/3o2u.wast new file mode 100644 index 000000000..ffa990f10 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/3o2u.wast @@ -0,0 +1,3744 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + ;; i + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/3o3u.wast b/benchmarks/pldi2026/wasp_btree/3o3u.wast new file mode 100644 index 000000000..0c191307c --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/3o3u.wast @@ -0,0 +1,3795 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 3 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + + ;; logical order: a>b>c + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + ;; i + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/4o1u.wast b/benchmarks/pldi2026/wasp_btree/4o1u.wast new file mode 100644 index 000000000..da4203391 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/4o1u.wast @@ -0,0 +1,3747 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/4o2u.wast b/benchmarks/pldi2026/wasp_btree/4o2u.wast new file mode 100644 index 000000000..7b3c6eecf --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/4o2u.wast @@ -0,0 +1,3798 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + ;; i + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/4o3u.wast b/benchmarks/pldi2026/wasp_btree/4o3u.wast new file mode 100644 index 000000000..30faaedda --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/4o3u.wast @@ -0,0 +1,3854 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 4 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;; logical order: a>b>c>d + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + ;; i + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/5o1u.wast b/benchmarks/pldi2026/wasp_btree/5o1u.wast new file mode 100644 index 000000000..9c6338700 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/5o1u.wast @@ -0,0 +1,3801 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/5o2u.wast b/benchmarks/pldi2026/wasp_btree/5o2u.wast new file mode 100644 index 000000000..cb2a650f1 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/5o2u.wast @@ -0,0 +1,3858 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + ;; i + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/5o3u.wast b/benchmarks/pldi2026/wasp_btree/5o3u.wast new file mode 100644 index 000000000..6342b1a5d --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/5o3u.wast @@ -0,0 +1,3915 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; logical order: a>b>c>d>e + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variable w/o order + ;; h + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + ;; i + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; j + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/6o1u.wast b/benchmarks/pldi2026/wasp_btree/6o1u.wast new file mode 100644 index 000000000..ccc8520f0 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/6o1u.wast @@ -0,0 +1,3861 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/6o2u.wast b/benchmarks/pldi2026/wasp_btree/6o2u.wast new file mode 100644 index 000000000..9038d51ee --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/6o2u.wast @@ -0,0 +1,3922 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + ;; i + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/6o3u.wast b/benchmarks/pldi2026/wasp_btree/6o3u.wast new file mode 100644 index 000000000..153c95b7a --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/6o3u.wast @@ -0,0 +1,3987 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 6 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + + ;; logical order: a>b>c>d>e>f + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + ;; i + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/7o1u.wast b/benchmarks/pldi2026/wasp_btree/7o1u.wast new file mode 100644 index 000000000..69e17d056 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/7o1u.wast @@ -0,0 +1,3926 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/7o2u.wast b/benchmarks/pldi2026/wasp_btree/7o2u.wast new file mode 100644 index 000000000..7c5b411a1 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/7o2u.wast @@ -0,0 +1,3992 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/7o3u.wast b/benchmarks/pldi2026/wasp_btree/7o3u.wast new file mode 100644 index 000000000..c51d9b646 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/7o3u.wast @@ -0,0 +1,4065 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 3 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + ;; i + (i32.const 1042) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/8o1u.wast b/benchmarks/pldi2026/wasp_btree/8o1u.wast new file mode 100644 index 000000000..3c9425018 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/8o1u.wast @@ -0,0 +1,3996 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/8o2u.wast b/benchmarks/pldi2026/wasp_btree/8o2u.wast new file mode 100644 index 000000000..9d19d9f7e --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/8o2u.wast @@ -0,0 +1,4059 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (sym_int32 "a") + (sym_int32 "b") + (i32.ne) + + ;;c + (sym_int32 "c") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (sym_int32 "d") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (sym_int32 "e") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (sym_int32 "f") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (sym_int32 "g") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (sym_int32 "x") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (sym_int32 "h") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + ;; i + (sym_int32 "i") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/9o1u.wast b/benchmarks/pldi2026/wasp_btree/9o1u.wast new file mode 100644 index 000000000..ef8a94483 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/9o1u.wast @@ -0,0 +1,4072 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; y + (i32.const 1046) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "x") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x>y + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + (get_sym_int32 "x") + (get_sym_int32 "y") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 1 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "y") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "y") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; y + (local.get 0) + (get_sym_int32 "y") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/9o2u.wast b/benchmarks/pldi2026/wasp_btree/9o2u.wast new file mode 100644 index 000000000..88a7615ab --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/9o2u.wast @@ -0,0 +1,4147 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 9 symbolic variables w/ order + ;; a and b + (i32.const 1024) + (i32.symbolic) + (i32.const 1026) + (i32.symbolic) + (i32.ne) + + ;;c + (i32.const 1028) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne) + + ;;d + (i32.const 1030) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne) + + ;;e + (i32.const 1032) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne) + + ;; f + (i32.const 1034) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (i32.const 1036) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; x + (i32.const 1044) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "x") + (get_sym_int32 "g") + (i32.ne) + + ;; y + (i32.const 1046) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "y") + (get_sym_int32 "x") + (i32.ne) + + ;; logical order: a>b>c>d>e>f>g>x>y + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s) + + (get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s) + + (get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s) + + (get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "x") + (i32.gt_s) + + (get_sym_int32 "x") + (get_sym_int32 "y") + (i32.gt_s) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (i32.const 1038) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "y") + (i32.ne) + + ;; i + (i32.const 1040) + (i32.symbolic) + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "x") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "y") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "c") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "d") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "e") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "x") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "y") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; e + (local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; x + (local.get 0) + (get_sym_int32 "x") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "x") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; y + (local.get 0) + (get_sym_int32 "y") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "y") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + ) + (export "main" (func $main)) + (data $0 (i32.const 1024) "a\00b\00c\00d\00e\00f\00g\00h\00i\00j\00x\00y\00") +) +(invoke "main") diff --git a/benchmarks/pldi2026/wasp_btree/BTree.wast b/benchmarks/pldi2026/wasp_btree/BTree.wast new file mode 100644 index 000000000..86cf3cbb7 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/BTree.wast @@ -0,0 +1,4073 @@ +(module + (memory $0 1) + + + (func $createBtree (param i32) (result i32) ;; createBtree(t), where t: degree of the btree + (i32.const 0) + (local.get 0) + (i32.store) ;; store t at address 0 + + (i32.const 0) + (i32.const 1) + (i32.store offset=4) ;; store the number of nodes in the btree = 1 + + (i32.const 0) + (i32.const 65536) + (i32.store offset=8) ;; store the root addr + + (i32.const 1) ;; Now create root + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then + (i32.const 65536) ;; 64KiB = 65536 bytes + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + + (i32.const 65536) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + ) + ) + (i32.const 65536) ;; returns the address of the root + ) + + ;; btreeSearch(x, k), where x: node address; k: key to search. Returns address of the key or -1 if key is not in tree. + (func $btreeSearch (param i32) (param i32) (result i32) (local i32) + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n -1 + (i32.le_s) ;; i <= x.children-1 + (if + (then + (local.get 1) ;; k + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + (if + (then + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) ;; i + + (local.get 0) ;; x + (i32.load offset=4) ;; x.children + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.le_s) ;; i <= x.children - 1 + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.eq) + ;; k == x.keys[i] + (if (result i32) + (then + + (local.get 0) ;; save the address, which is x+8+i*4 + (i32.const 8) + (i32.add) ;; x+8 + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x+8+i*4 + + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + (else + (local.get 0) ;; x + (i32.load) ;; x is leaf? + (i32.const 1) ;; if == 1, then yes + (i32.eq) + (if (result i32) + (then + (i32.const -1) + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i + + (local.get 1) ;; k + + (call $btreeSearch) ;; btreeSearch(x.children[i], k) + + ) + ) + ) + ) + ) + + ;; btreeSplitChild(x, i), where x: addr of a non full internal node; i: index such that x.children[i] is a full child of x + (func $btreeSplitChild (param i32) (param i32) (local i32) (local i32) + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if ;; if we can grow memory + (then ;; get the number of nodes in the tree + (i32.const 0) + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address is 64KiB*(number of nodes+1) + (local.set 2) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + + (i32.load offset=8) ;; load the addr of the child in index i : y + + + (i32.load) ;; check if x.children[i] is leaf ;; load the first i32 in the child + (i32.const 1) + (i32.eq) ;; is y leaf? + (if + (then ;; yes + (local.get 2) ;; addr of new node z + (i32.const 1) + (i32.store) ;; store 1(TRUE) regarding if node is leaf + ) + (else ;; no + (local.get 2) ;; addr of new node z + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + ) + ) + + (local.get 2) ;; now store number of children, which will be t/2 -1 ;; addr of z + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + + (i32.store offset=4) ;; store number of children = (t/2)-1 + + (i32.const 0) ;; now to store the keys + (local.set 3) ;; counter = 0 + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.const 1) + (i32.sub) ;; (t/2)-1 + (i32.eq) ;; counter == (t/2)-1 + (if + (then + + (br $loop_break) + ) + (else + + (local.get 2) ;; addr of z ;; we will store in the new node's address. z.keys[counter] + + (i32.const 4) + (local.get 3) ;; counter + + (i32.mul) ;; counter * 4 + + (i32.add) ;; addr + counter * 4 -> where the key is goint to be located + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 4) ;; now get x.children[i].keys[counter+(t/2)] + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.add) ;; counter + (t/2) + + (i32.mul) ;; counter + (t/2) *4 + + (i32.add) ;; y + counter + (t/2) *4 + (i32.load offset=8) ;; y.keys[counter + (t/2)] + + (i32.store offset=8) ;; z.keys[counter] = y.keys[counter + (t/2)] + + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + + ) + ) + ) + ) + + (i32.const 0) + (local.set 3) ;; set counter back to 0 + + (i32.const 0) ;; check if x.children[i] is leaf + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + i*4 + (i32.load offset=8) ;; load the address of the child in index i = y + (i32.load) ;; get first i32 in child --> isLeaf + (i32.const 1) + (i32.ne) ;; is leaf? + + (if + (then ;; not leaf so we have to update the children + (block $loop_break + (loop $loop + + (local.get 3) ;; counter + + (i32.const 0) + (i32.load) ;; t + + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.eq) ;; counter == (t/2) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; now get z.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; counter*4 + + (i32.add) ;; (t-1)*4 + counter*4 + + (local.get 2) ;; z + (i32.add) ;; z + (t-1)*4 + counter*4 --> address where addr of child is stored + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) ;; get x.children[i].children[counter+(t/2)] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.add) ;; counter + t/2 + (i32.const 4) + (i32.mul) ;; counter+t/2 * 4 + + (i32.add) ;; (t-1)*4 + (counter+(t/2))*4 + + (i32.add) ;; x.children[i] + (t-1)*4 + (counter + (t/2))*4 + (i32.load offset=8) ;; load the address of the child in index counter + t/2 + + (i32.store offset=8) ;; z.children[counter] = x.children[i].children[counter] + + (local.get 3) ;; increment counter + (i32.const 1) + (i32.add) + (local.set 3) + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.store offset=4) ;; number of keys of x.children[i] is now t/2 -1 + + (local.get 0) ;; x + + (i32.load offset=4) ;; get x.n + (local.set 3) ;; counter = x.n + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (local.get 3) ;; counter + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; get x.children[counter + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (i32.add) ;; (t-1)*4 + (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter + 1)*4 -->address where addr of child is stored + + (i32.const 0) ;; get x.children[counter] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (i32.add) ;; (t-1)*4 + (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (counter)*4 + (i32.load offset=8) ;; load the addr of the child in index (counter) + + (i32.store offset=8) ;; x.children[counter+1] = x.children[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (i32.const 0) ;; get x.children[i + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 1) + (i32.add) ;; i + 1 + (i32.const 4) + (i32.mul) ;; (i + 1)*4 + + (i32.add) ;; (t-1)*4 + (i + 1)*4 + + (local.get 0) ;; x + + (i32.add) ;; x + (t-1)*4 + (i + 1)*4 --> addr where we will store the new addr of the child + + (local.get 2) ;; addr of z + (i32.store offset=8) ;; x.children[i+1] = z + + (local.get 0) ;; x + (i32.load offset=4) ;; get x.n + (i32.const 1) + (i32.sub) + (local.set 3) ;; counter = x.n -1 + + (block $loop_break + (loop $loop + (local.get 1) ;; i + (i32.const 1) + (i32.sub) ;; i-1 + (local.get 3) ;; counter + (i32.eq) ;; counter == i-1 + + (if + (then + (br $loop_break) + ) + (else + + (local.get 3) ;; get x.keys[counter + 1] ;; counter + (i32.const 1) + (i32.add) ;; counter + 1 + (i32.const 4) + (i32.mul) ;; (counter + 1)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter + 1)*4 --> addr where we will store the new key + + (local.get 3) ;; counter + (i32.const 4) + (i32.mul) ;; (counter)*4 + + (local.get 0) ;; x + (i32.add) ;; x +(counter)*4 + (i32.load offset=8) ;; load the key in index (counter) + + (i32.store offset=8) ;; x.keys[counter+1] = x.keys[counter] + + (local.get 3) ;; decrement counter + (i32.const 1) + (i32.sub) + (local.set 3) + (br $loop) + ) + ) + + ) + ) + + (local.get 1) ;; get x.keys[i] + (i32.const 4) + (i32.mul) ;; i*4 + + (local.get 0) ;; x + (i32.add) ;; x +i*4 --> addr of the key + + (i32.const 0) ;; get x.children[i].keys[t/2] + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; t/2 -1 + + (i32.const 4) + (i32.mul) ;; (t/2)-1 *4 + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 1) ;; i + (i32.const 4) + (i32.mul) ;; (i)*4 + + (i32.add) ;; (t-1)*4 + (i)*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i)*4 + (i32.load offset=8) ;; load the address of the child in index (i) + + (i32.add) ;; y + (t/2)-1 *4 + (i32.load offset=8) ;; load the key in index (t/2)-1 from node x.children[i] + + (i32.store offset=8) ;; store the new key in the addr + + (local.get 0) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) ;; x.n + 1 + (i32.store offset=4) ;; x.n = x.n + 1 + ) + ) + ) + + ;; btreeInsertNonFull(x, k), where x: addr of a non full internal node; k: the key to insert + (func $btreeInsertNonFull (param i32) (param i32) (local i32) + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.const 1) + (i32.sub) ;; x.n -1 + (local.set 2) ;; i = x.n -1 + + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (block $loop_break + (loop $loop + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + + (if (result i32) + (then + (local.get 1) ;; k + (local.get 0) ;; x + ;; x+4*i + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + (i32.lt_s) ;; k < x.keys[i] + ) + (else + (i32.const 0) + ) + ) + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i <= 0? + (i32.and) + + (if + (then + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i *4 + + (i32.add) ;; x + i *4 --> addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.keys[i+1] = x.keys[i] + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 2) ;; i = i-1 + (br $loop) + + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.mul) ;; i+1 *4 + + (i32.add) ;; x + i+1 *4 --> addr of x.keys[i+1] + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.keys[i+1] = k + + (local.get 0) + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;; x.n = x.n +1 + + ) + (else ;; x is not leaf + (block $loop_break + (loop $loop + + (local.get 2) ;; i + (i32.const 0) + (i32.ge_s) ;; i >= 0 + + (if + (then + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.lt_s) ;; k < x.keys[i] + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i -1 + (local.set 2) ;; i = i-1 + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + + (i32.const 1) + (i32.add) + + (local.set 2) ;;i = i+1 + + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address of the child in index i = y + (i32.load offset=8) ;; load the address of the child in index i = y + + (i32.load offset=4) ;; get y.n + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; y.n == t-1 --> node is full + (if + (then + (local.get 0) ;; x + + (local.get 2) ;; i + (call $btreeSplitChild) + + (local.get 1) ;; k + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k>x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i+1 + ) + ) + ) + ) + + (i32.const 0) ;; get x.children[i] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; load the address of the child in index i = y + + (local.get 1) ;; k + + (call $btreeInsertNonFull) + + ) + ) + ) + + (func $btreeInsert (param i32) (result i32) (local i32) (local i32) + (i32.const 0) + (i32.load offset=8) ;; root addr + (local.tee 2) ;; set r + + (i32.load offset=4) ;; r.n + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.eq) ;; r.n == t-1 --> root is full + (if (result i32) + (then + + (i32.const 1) ;; create a new node + (memory.grow) ;; create new page + (i32.const -1) + (i32.ne) + (if (result i32) ;; if we can grow memory + (then + (i32.const 0) ;; get the number of nodes in the tree + (i32.load offset=4) ;; number of nodes in the tree + (i32.const 1) + (i32.add) ;; number of nodes + 1 + (i32.const 65536) + (i32.mul) ;; address of s is 64KiB*(number of nodes+1) + (local.set 1) + + (i32.const 0) ;; change number of nodes + (i32.const 0) + (i32.load offset=4) + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; set number of nodes to + 1 + + (i32.const 0) + (local.get 1) ;; s + (i32.store offset=8) ;; root addr is now s + + (local.get 1) ;; s + (i32.const 0) + (i32.store) ;; store 0(FALSE) regarding if node is leaf + + (local.get 1) ;; now store number of keys + (i32.const 0) + (i32.store offset=4) ;; store number of keys = 0 + + (i32.const 0) ;; store children addresses + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 1) ;; x + (i32.add) ;; x + (t-1)*4 --> addre where addr of child number 0 is located + (local.get 2) + + (i32.store offset=8) ;; s.children[0] = r + + (local.get 1) ;; s + (i32.const 0) + + (call $btreeSplitChild) + + (local.get 1) ;; s + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 1) ;; return the address of the new root + ) + (else + (i32.const -1) ;; return -1 because we could not create a new node + ) + ) + ) + (else + (local.get 2) ;; r + (local.get 0) ;; k + (call $btreeInsertNonFull) + (local.get 2) ;; return the address of the root, which is the same + ) + ) + ) + + ;; Returns the address of the new root (if applicable, otherwise returns the addres of the root) + (func $btreeDelete (param i32) (param i32) (result i32) (local i32) (local i32) (local i32) (local i32) + (local.get 0) ;; x + (i32.load) ;; get first i32 --> isLeaf + (i32.const 1) + (i32.eq) ;; is leaf? + (if + (then ;; x is leaf + (i32.const 0) + (local.set 2) ;; i = 0 + (block $loop_break + (loop $loop + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (local.get 2) ;; i + + (i32.eq) ;; i == x.n + (if + (then + (br $loop_break) ;; break from loop + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + + (i32.eq) ;; k == x.keys[i] + (if + (then + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $while_break + (loop $while + (local.get 3) ;; j + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n-1 + (i32.eq) ;; j == x.n-1 + (if + (then + (br $while_break) + ) + (else + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + + (i32.add) ;; x + j*4 --> addr where x.keys[j] is stored + + (local.get 0) ;; x + + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.mul) ;; j+1 *4 + + (i32.add) ;; x + j+1 *4 --> addr where x.keys[j+1] is stored + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $while) + ) + ) + + ) + ) + (local.get 0) ;; x + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.n = x.n -1 + (br $loop_break) + ) + + ) + ) + + ) + (i32.const 1) + (local.get 2) + (i32.add) + (local.set 2) ;; i = i+1 + (br $loop) ;; continue + ) + ) + ) + (else ;; x is not leaf + + (i32.const 0) ;;get the index of the appropriate child/key + (local.set 2) ;; i = 0 + + (block $loop_break + (loop $loop + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (if (result i32) + (then + (local.get 1) ;; k + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (i32.gt_s) ;; k > x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (local.get 2) ;; i + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.le_s) ;; i <= x.n - 1 + + (i32.and) ;; i <= x.n - 1 && k > x.keys[i] + + (if + (then + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (local.set 2) ;; i = i + 1 + + (br $loop) + ) + (else + (br $loop_break) + ) + ) + ) + ) + (local.get 2) + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.lt_s) ;; i < x.n + (if (result i32) + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[i] + + (local.get 1) ;; k + (i32.eq) ;; k == x.keys[i] + ) + (else + (i32.const 0) + ) + ) + (if + (then ;; key is present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.tee 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i].n >= t/2 + (if + (then + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.sub) ;; index = x.c[i].n - 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[x.c[i].n - 1] + + (call $btreeDelete) ;; (x.c[i], x.c[i].keys[x.c[i].n - 1]) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i].keys[x.c[i].n - 1] + + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i+1] + (local.tee 5) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (local.get 5) ;; x.c[i+1] + (local.get 5) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[0] + (call $btreeDelete) + (drop) + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + ) + (else + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i *4 + (i32.add) ;; x + i*4 --> addr where x.c[i].keys[x.c[i].n] will be stored + + (local.get 1) ;; k + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = k + + (i32.const 0) ;; now merge x.c[i] with x.c[i+1] + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + (i32.add) ;; (t-1)*4 + i+1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + + (if ;; j == x.c[i+1].n + (then + (br $loop_break) + ) + (else + + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n + j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[index] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x.c[i+1] + i*4 ;; addr of x.c[i+1].keys[j] + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[index] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + + ) + + ) + ) + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n +1 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.add) + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + 1 + x.c[i+1].n + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + + (i32.const 0) ;; now adjust the children + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.get 3) ;; j + (i32.add) ;; index = x.c[i].n+j + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x.c[i] + (t-1)*4 --> address where x.c[i].c[x.c[i].n+j] is stored + + (i32.const 0) ;;get x.c[i+1].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x.c[i+1] + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + (i32.const 1) + (i32.sub) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; j*4 + (i32.add) ;; x + j*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.add) + (i32.mul) ;; j+1*4 + (i32.add) ;; x + j+1*4 ;; addr of x.keys[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + + ) + ) + + (local.get 2) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = i+1 + + (block $loop_break + (loop $loop + (local.get 0) + (i32.load offset=4) + + (local.get 3) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.add) ;; j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + (local.get 0) + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + (i32.store offset=4) ;; x.n = x.n-1 + + (local.get 5) ;; x.c[i] + (local.get 1) ;; k + + (call $btreeDelete) + (drop) + + ) + ) + + ) + ) + + ) + (else ;; key not present in node x + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 4) + (i32.mul) ;; i*4 + + (i32.add) ;; (t-1)*4 + i*4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> address where addr of child in index i is located + (i32.load offset=8) ;; x.c[i] + + (local.set 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) + (i32.const 1) + (i32.sub) ;; t/2 - 1 + + (i32.eq) + + (if + (then + (i32.const -1) + (local.set 4) ;; changed = -1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.le_s) ;; i+1 <= x.n + + (if + (then + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i+1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i+1].n >= t/2 + + (if + (then + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.const 1) + (i32.sub) ;; index = t/2 -1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[t/2-1] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[t/2-1] = x.keys[i] + + (local.get 5) + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + + (i32.store offset=4) ;;x.c[i].n = x.c[i].n +1 + + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i+1].keys[0] + (i32.load offset=8) ;; x.c[i+1].keys[0] + + (i32.store offset=8) ;; x.keys[i] = x.c[i+1].keys[0] + + (local.get 5) + (i32.load) ;; x.c[i] is leaf? + (i32.const 1) + (i32.ne) + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + + (i32.const 0) ;;get x.c[i].c[t/2] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; index = t/2 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[t/2] + + (i32.const 0) ;;get x.c[i+1].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[0] + + (i32.store offset=8) ;; x.c[i].c[t/2] = x.c[i+1].c[0] + ) + ) + + (local.get 5) ;; x.c[i] + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + (i32.store offset=4) ;; x.c[i].n = t/2 + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 --> address where x.c[i+1].keys[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j+1] + + (i32.store offset=8) ;; x.c[i+1].keys[j] = x.c[i+1].keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if ;; if x.c[i] is not leaf, we have to adjust children + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 --> address where x.c[i+1].c[j] is located + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j+1 + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j+1] + + (i32.store offset=8) ;; x.c[i+1].c[j] = x.c[i+1].c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j+1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr where x.c[i+1] is located + (i32.load offset=8) + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i+1].n = x.c[i+1].n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + (i32.const 0) + (i32.ge_s) ;; i -1 >= 0 + + (i32.and) ;; changed == -1 && i -1 >= 0 + + (if + (then + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 0) + (i32.load) ;; t + (i32.const 2) + (i32.div_s) ;; t/2 + + (i32.ge_s) ;; x.c[i-1].n >= t/2 + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (local.set 3) ;; j = x.c[i].n + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[j-1] + (i32.load offset=8) ;; x.c[i].keys[j-1] + + (i32.store offset=8) ;; x.c[i].keys[j] = x.c[i].keys[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + + (if + (then + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (local.set 3) ;; j = x.c[i].n + 1 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) + (i32.eq) + + (if + (then + (br $loop_break) + ) + (else + (i32.const 0) ;;get x.c[i].c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> address where x.c[i].c[j] is located + + (i32.const 0) ;;get x.c[i].c[j-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; j + (i32.const 1) + (i32.sub) ;; j-1 + (i32.const 4) + (i32.mul) ;; j *4 + + (i32.add) ;; (t-1)*4 + j *4 + + (local.get 5) ;; x.c[i] + (i32.add) + (i32.load offset=8) ;; x.c[i].c[j-1] + + (i32.store offset=8) ;; x.c[i].c[j] = x.c[i].c[j-1] + + (local.get 3) + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = j-1 + + (br $loop) + ) + ) + ) + ) + ) + ) + + (local.get 5) + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) + (i32.store offset=4) ;; ;; x.c[i].n = x.c[i].n + 1 + + (local.get 5) ;; x.c[i] + (i32.const 4) + (i32.const 0) ;; index = 0 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[0] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i-1] + + (i32.store offset=8) ;; x.c[i].keys[0] = x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) + (i32.load offset=4) ;; x.c[i-1].n + + (i32.const 1) + (i32.sub) + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n - 1 + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; index = i-1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + (i32.load offset=8) + + (i32.store offset=8) ;; x.keys[i-1] = x.c[i-1].keys[x.c[i-1].n] + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + + (i32.const 0) ;; get x.c[i].c[0] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 ;; addr where x.c[i].c[0] is located + + (i32.const 0) ;; get x.c[i-1].c[x.c[i-1].n + 1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (i32.const 1) + (i32.add) ;; index = x.c[i-1.n + 1] + + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1].c[x.c[i-1].n + 1] + + (i32.store offset=8) ;; x.c[i].c[0] = x.c[i-1].c[x.c[i-1].n + 1] + + ) + ) + (i32.const 0) + (local.set 4) ;; changed = 0 + ) + ) + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) + (if ;; changed == -1? + (then + + (local.get 2) ;; we have to merge x.c[i] with one sibling;; i + (i32.const 1) + (i32.add) ;; i+1 + + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + + (i32.le_s) + (if ;; i+1 <= x.n + (then + + (local.get 5) ;; merge with right sibling;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) ;; index = x.c[i].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n] = x.keys[i] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + (local.get 5) ;; x.c[i] + (i32.const 4) + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i].keys[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i+1].keys[j] + + (i32.store offset=8) ;; x.c[i].keys[x.c[i].n+j] = x.c[i+1].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i+1].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 5) + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i].c[x.c[i].n+j] + + (i32.const 0) ;;get x.c[i].c[x.c[i].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1].c[j] + + (i32.store offset=8) ;; x.c[i].c[x.c[i].n+j] = x.c[i+1].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (local.get 5) ;; x.c[i] + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.const 0) ;;get x.c[i+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i+1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i+1] + (i32.load offset=4) ;; x.c[i+1].n + + (i32.add) ;; x.c[i].n + x.c[i+1].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i].n = x.c[i].n + x.c[i+1].n + 1 + + (local.get 2) ;; i + (i32.const 1) + (i32.add) ;; i+1 + (local.set 3) ;; j = i+1 + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j+1] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + ) + ) + (local.get 2) ;; i + (local.set 3) ;; j = i + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + + (i32.const 0) + (local.set 4) ;; changed = 0 + + ) + ) + + (local.get 4) ;; changed + (i32.const -1) + (i32.eq) ;; changed == -1 ? + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) ;; i - 1 + + (i32.const 0) + (i32.ge_s) ;; i - 1 >= 0? + + (i32.and) ;; changed == -1 && i - 1 >= 0 + (if + (then + + (i32.const 0) ;; merge with left sibling ;;get x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; index = x.c[i-1].n + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n] + + (local.get 0) ;; x + (i32.const 4) + (local.get 2) ;; index = i + (i32.const 1) + (i32.sub) ;; index = i-1 + + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[i-1] + (i32.load offset=8) ;; x.keys[i] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n] = x.keys[i-1] + + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;; x.c[i-1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.const 4) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.c[i-1].keys[x.c[i-1].n+j] + + (local.get 5) ;; x.c[i] + (i32.const 4) + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.c[i].keys[j] + + (i32.store offset=8) ;; x.c[i-1].keys[x.c[i-1].n+j] = x.c[i].keys[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + + (local.get 5) + (i32.load) + (i32.const 1) + (i32.ne) + (if + (then + (i32.const 0) + (local.set 3) ;; j = 0 + + (block $loop_break + (loop $loop + (local.get 3) ;; j + + (local.get 5) ;; x.c[i] + (i32.load offset=4) ;; x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + 1 + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[i-1].c[x.c[i-1].n+j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) + (local.get 3) + (i32.add) + (i32.const 1) + (i32.add) ;; index = x.c[i-1].n+j+1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.add) ;; x + (t-1)*4 --> addr of x.c[i-1].c[x.c[i-1].n+j] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 5) ;; x.c[i] + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i].c[j] + + (i32.store offset=8) ;; x.c[i-1].c[x.c[i-1].n+j] = x.c[i].c[j] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + (br $loop) + ) + ) + + ) + ) + ) + ) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (i32.load offset=4) ;; x.c[i-1].n + + (local.get 5) + (i32.load offset=4) ;; x.c[i].n + + (i32.add) ;; x.c[i-1].n + x.c[i].n + (i32.const 1) + (i32.add) ;; x.c[i].n + x.c[i+1].n + 1 + + (i32.store offset=4) ;; x.c[i-1].n = x.c[i-1].n + x.c[i].n + 1 + + (local.get 2) ;; i + (local.set 3) ;; j = i + + (block $loop_break ;; re-organize x + (loop $loop + + (local.get 3) + + (local.get 0) + (i32.load offset=4) ;; x.n + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (i32.const 0) ;;get x.c[j] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) ;; index = j + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + + (i32.const 0) ;;get x.c[j+1] + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.const 4) + (i32.mul) ;; i-1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 --> addr of x.c[j] + (i32.load offset=8) ;; x.c[j+1] + + (i32.store offset=8) ;; x.c[j] = x.c[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (local.set 3) ;; j = i - 1 + (block $loop_break + (loop $loop + + (local.get 3) ;; j + + (local.get 0) + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) + + (i32.eq) + (if + (then + (br $loop_break) + ) + (else + + (local.get 0) ;; x + (i32.const 4) + + (local.get 3) ;; index = j + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 ;; addr of x.keys[j] + + (local.get 0) ;; x + (i32.const 4) + (local.get 3) + (i32.const 1) + (i32.add) ;; index = j + 1 + (i32.mul) ;; i*4 + (i32.add) ;; x + i*4 + (i32.load offset=8) ;; x.keys[j+1] + + (i32.store offset=8) ;; x.keys[j] = x.keys[j+1] + + (local.get 3) + (i32.const 1) + (i32.add) + (local.set 3) ;; j = j + 1 + + (br $loop) + + ) + ) + + ) + ) + (local.get 0) ;; x + (local.get 0) ;; x + (i32.load offset=4) ;; x.n + (i32.const 1) + (i32.sub) ;; x.n - 1 + (i32.store offset=4) ;; x.n = x.n - 1 + ) + ) + ) + ) + ) + ) + (local.get 4) + (i32.const -1) + (i32.eq) + (if ;; changed == -1? if yes, we merged with left sibling + (then + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (local.get 2) ;; i + (i32.const 1) + (i32.sub) + (i32.const 4) + (i32.mul) ;; i+1 *4 + + (i32.add) ;; (t-1)*4 + i-1 *4 + + (local.get 0) ;; x + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; x.c[i-1] + (local.get 1) + (call $btreeDelete) + (drop) + ) + (else + (local.get 5) ;; x.c[i] + (local.get 1) + (call $btreeDelete) + (drop) + ) + ) + + ) + ) + ) ;; end of if x is not leaf + ) + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.load offset=4) + (i32.const 0) + (i32.eq) + (if ;; if root is empty + (then + (i32.const 0) + + (i32.const 0) + (i32.load) ;; t + (i32.const 1) + (i32.sub) ;; t-1 + (i32.const 4) + (i32.mul) ;; (t-1)*4 + + (i32.const 0) ;; index = 0 + (i32.const 4) + (i32.mul) ;; i *4 + + (i32.add) ;; (t-1)*4 + i *4 + + (i32.const 0) + (i32.load offset=8) ;; root addr + (i32.add) ;; x + (t-1)*4 + (i32.load offset=8) ;; root.c[0] + + (i32.store offset=8) ;; root = root.c[0] + ) + ) + + (i32.const 0) + (i32.load offset=8) ;; root addr + ) + + + (func $main + (local i32) + (i32.const 4) ;;create a tree with degree 4 + (call $createBtree) + (local.set 0) + + ;; 5 symbolic variables w/ order + ;; a and b + (sym_int32 "a") + (sym_int32 "b") + (i32.ne) + + (;);;c + (sym_int32 "c") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "c") + (get_sym_int32 "b") + (i32.ne);) + + (;);;d + (sym_int32 "d") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "d") + (get_sym_int32 "c") + (i32.ne);) + + (;;;e + (sym_int32 "e") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "e") + (get_sym_int32 "d") + (i32.ne);) + + (;);; f + (sym_int32 "f") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "f") + (get_sym_int32 "e") + (i32.ne) + + ;; g + (sym_int32 "g") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "g") + (get_sym_int32 "f") + (i32.ne) + + ;; z + (sym_int32 "z") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "b") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "c") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "d") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "e") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "z") + (get_sym_int32 "g") + (i32.ne);) + + + + ;; logical order: a>b>c>d>e>f>g>z + (get_sym_int32 "a") + (get_sym_int32 "b") + (i32.gt_s) + + (;(get_sym_int32 "b") + (get_sym_int32 "c") + (i32.gt_s);) + + (;(get_sym_int32 "c") + (get_sym_int32 "d") + (i32.gt_s);) + + (;(get_sym_int32 "d") + (get_sym_int32 "e") + (i32.gt_s);) + + (;(get_sym_int32 "e") + (get_sym_int32 "f") + (i32.gt_s) + + (get_sym_int32 "f") + (get_sym_int32 "g") + (i32.gt_s) + + (get_sym_int32 "g") + (get_sym_int32 "z") + (i32.gt_s);) + + + (i32.and) + + ;; 2 symbolic variables w/o order + ;; h + (sym_int32 "h") + (sym_int32 "a") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "h") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "h") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "h") + (get_sym_int32 "z") + (i32.ne);) + + + + ;; i + (sym_int32 "i") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "i") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "i") + (get_sym_int32 "f") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "g") + (i32.ne) + + (get_sym_int32 "i") + (get_sym_int32 "z") + (i32.ne);) + + + (get_sym_int32 "i") + (get_sym_int32 "h") + (i32.ne) + + + ;; j + (sym_int32 "j") + (get_sym_int32 "a") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "b") + (i32.ne) + + (;(get_sym_int32 "j") + (get_sym_int32 "c") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "d") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "e") + (i32.ne);) + + (;(get_sym_int32 "j") + (get_sym_int32 "f") + (i32.ne) + + (;(get_sym_int32 "j") + (get_sym_int32 "g") + (i32.ne););) + + (get_sym_int32 "j") + (get_sym_int32 "h") + (i32.ne) + + (get_sym_int32 "j") + (get_sym_int32 "i") + (i32.ne) + + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assume) + + ;; insert variables + (get_sym_int32 "a") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "b") + (call $btreeInsert) + (local.set 0) + (;(get_sym_int32 "c") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "d") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "e") + (call $btreeInsert) + (local.set 0);) + (;(get_sym_int32 "f") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "g") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "z") + (call $btreeInsert) + (local.set 0);) + (get_sym_int32 "h") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "i") + (call $btreeInsert) + (local.set 0) + (get_sym_int32 "j") + (call $btreeInsert) + (local.set 0) + + (print_btree) + + ;; search for variables & check that they were inserted + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (;(local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + (;(local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "z") + (call $btreeSearch) + (i32.const -1) + (i32.ne);) + + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (local.get 0) + (get_sym_int32 "j") + (call $btreeSearch) + (i32.const -1) + (i32.ne) + + (i32.and) + (i32.and) + (i32.and) + (i32.and) + (sym_assert) + + ;; delete & check that it was deleted + ;; a + (local.get 0) + (get_sym_int32 "a") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "a") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; b + (local.get 0) + (get_sym_int32 "b") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "b") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + (;);; c + (local.get 0) + (get_sym_int32 "c") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "c") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + (;);; d + (local.get 0) + (get_sym_int32 "d") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "d") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + ;; e + (;(local.get 0) + (get_sym_int32 "e") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "e") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + (;);; f + (local.get 0) + (get_sym_int32 "f") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "f") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; g + (local.get 0) + (get_sym_int32 "g") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "g") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; z + (local.get 0) + (get_sym_int32 "z") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "z") + (call $btreeSearch) + (i32.const -1) + (i32.eq);) + + ;; h + (local.get 0) + (get_sym_int32 "h") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "h") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + ;; i + (local.get 0) + (get_sym_int32 "i") + (call $btreeDelete) + (local.set 0) + + (local.get 0) + (get_sym_int32 "i") + (call $btreeSearch) + (i32.const -1) + (i32.eq) + + + (print_btree) + + (i32.and) + (i32.and) + (i32.and) + + (sym_assert) + + + + ) + (export "main" (func $main)) + +) +(invoke "main") From cf6b6898e4992a34d003d6cc2004b612580278dc Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:04:32 -0500 Subject: [PATCH 091/105] update collection-c benchmark --- .../array/array_test_add.wat | 906 ++++++ .../array/array_test_addAt2.wat | 1072 +++++++ .../array/array_test_contains.wat | 991 ++++++ .../array/array_test_deepCopy.wat | 1148 +++++++ .../array/array_test_getAt.wat | 892 ++++++ .../array/array_test_indexOf.wat | 904 ++++++ .../array/array_test_iterAdd.wat | 1479 +++++++++ .../array/array_test_iterRemove.wat | 1342 ++++++++ .../array/array_test_iterReplace.wat | 1271 ++++++++ .../array/array_test_reduce.wat | 1055 +++++++ .../array/array_test_remove.wat | 1167 +++++++ .../array/array_test_removeAll.wat | 864 ++++++ .../array/array_test_removeAt.wat | 1137 +++++++ .../array/array_test_replaceAt.wat | 960 ++++++ .../array/array_test_reverse.wat | 990 ++++++ .../array/array_test_shallowCopy.wat | 1033 +++++++ .../array/array_test_subarray.wat | 1120 +++++++ .../array/array_test_zipIterAdd.wat | 1961 ++++++++++++ .../array/array_test_zipIterNext.wat | 1229 ++++++++ .../array/array_test_zipIterRemove.wat | 1696 +++++++++++ .../array/array_test_zipIterReplace.wat | 1712 +++++++++++ .../deque/deque_test_addAt1.wat | 1751 +++++++++++ .../deque/deque_test_addAt2.wat | 1773 +++++++++++ .../deque/deque_test_addAt3.wat | 1773 +++++++++++ .../deque/deque_test_addAt4.wat | 1773 +++++++++++ .../deque/deque_test_addAt5.wat | 1773 +++++++++++ .../deque/deque_test_addFirst.wat | 1112 +++++++ .../deque/deque_test_addLast.wat | 1075 +++++++ .../deque/deque_test_bufferExpansion.wat | 1227 ++++++++ .../deque/deque_test_capacity.wat | 1064 +++++++ .../deque/deque_test_contains.wat | 1175 +++++++ .../deque/deque_test_copyDeep.wat | 1478 +++++++++ .../deque/deque_test_copyShallow.wat | 1275 ++++++++ .../deque/deque_test_filter1.wat | 1349 ++++++++ .../deque/deque_test_filter2.wat | 1348 ++++++++ .../deque/deque_test_filter3.wat | 1326 ++++++++ .../deque/deque_test_filterMut1.wat | 1968 ++++++++++++ .../deque/deque_test_filterMut2.wat | 1971 ++++++++++++ .../deque/deque_test_filterMut3.wat | 1941 ++++++++++++ .../deque/deque_test_getAt.wat | 1118 +++++++ .../deque/deque_test_getFirst.wat | 1137 +++++++ .../deque/deque_test_getLast.wat | 1149 +++++++ .../deque/deque_test_iterAdd.wat | 2154 +++++++++++++ .../deque/deque_test_iterNext.wat | 1373 +++++++++ .../deque/deque_test_iterRemove.wat | 2142 +++++++++++++ .../deque/deque_test_removeAll.wat | 1188 ++++++++ .../deque/deque_test_removeFirst.wat | 1257 ++++++++ .../deque/deque_test_removeLast.wat | 1272 ++++++++ .../deque/deque_test_reverse.wat | 1263 ++++++++ .../deque/deque_test_size.wat | 1056 +++++++ .../deque/deque_test_trimCapacity.wat | 1169 +++++++ .../deque/deque_test_zipIterAdd.wat | 2706 +++++++++++++++++ .../deque/deque_test_zipIterNext.wat | 1587 ++++++++++ .../deque/deque_test_zipIterRemove.wat | 2574 ++++++++++++++++ .../deque/deque_test_zipIterReplace.wat | 2065 +++++++++++++ .../list/list_test_add.wat | 926 ++++++ .../list/list_test_addAll.wat | 1701 +++++++++++ .../list/list_test_addAllAt.wat | 1652 ++++++++++ .../list/list_test_addAt.wat | 1425 +++++++++ .../list/list_test_addFirst.wat | 924 ++++++ .../list/list_test_addLast.wat | 889 ++++++ .../list/list_test_contains.wat | 1008 ++++++ .../list/list_test_copyDeep.wat | 1416 +++++++++ .../list/list_test_copyShallow.wat | 1383 +++++++++ .../list/list_test_filter1.wat | 1288 ++++++++ .../list/list_test_filter2.wat | 1404 +++++++++ .../list/list_test_getAt.wat | 1189 ++++++++ .../list/list_test_getLast.wat | 1035 +++++++ .../list/list_test_indexOf.wat | 1004 ++++++ .../list/list_test_iterAdd.wat | 1752 +++++++++++ .../list/list_test_iterDescAdd.wat | 1755 +++++++++++ .../list/list_test_iterDescRemove.wat | 1598 ++++++++++ .../list/list_test_iterRemove.wat | 1519 +++++++++ .../list/list_test_mutFilter1.wat | 1254 ++++++++ .../list/list_test_mutFilter2.wat | 1374 +++++++++ .../list/list_test_new.wat | 750 +++++ .../list/list_test_remove.wat | 1451 +++++++++ .../list/list_test_removeAll.wat | 1076 +++++++ .../list/list_test_removeAt.wat | 1319 ++++++++ .../list/list_test_removeFirst.wat | 1123 +++++++ .../list/list_test_removeLast.wat | 1127 +++++++ .../list/list_test_replaceAt.wat | 1282 ++++++++ .../list/list_test_reverse.wat | 1711 +++++++++++ .../list/list_test_sort.wat | 1362 +++++++++ .../list/list_test_splice.wat | 1627 ++++++++++ .../list/list_test_spliceAt.wat | 1601 ++++++++++ .../list/list_test_sublist.wat | 1406 +++++++++ .../list/list_test_toArray.wat | 1342 ++++++++ .../list/list_test_zipIterAdd.wat | 2331 ++++++++++++++ .../list/list_test_zipIterNext.wat | 1231 ++++++++ .../list/list_test_zipIterRemove.wat | 1760 +++++++++++ .../list/list_test_zipIterReplace.wat | 1841 +++++++++++ .../pqueue/pqueue_test_enqueue.wat | 1434 +++++++++ .../pqueue/pqueue_test_pop.wat | 1657 ++++++++++ .../queue/queue_test_enqueue.wat | 1319 ++++++++ .../queue/queue_test_iter.wat | 1460 +++++++++ .../queue/queue_test_poll.wat | 1417 +++++++++ .../queue/queue_test_zipIterNext.wat | 1745 +++++++++++ .../ring_buffer/ring_buffer_test_capacity.wat | 927 ++++++ .../ring_buffer/ring_buffer_test_dequeue.wat | 865 ++++++ .../ring_buffer/ring_buffer_test_enqueue.wat | 791 +++++ .../slist/slist_test_add.wat | 809 +++++ .../slist/slist_test_addAll.wat | 1124 +++++++ .../slist/slist_test_addAllAt.wat | 1336 ++++++++ .../slist/slist_test_addAt.wat | 1217 ++++++++ .../slist/slist_test_addFirst.wat | 862 ++++++ .../slist/slist_test_addLast.wat | 772 +++++ .../slist/slist_test_contains.wat | 768 +++++ .../slist/slist_test_copyDeep.wat | 1223 ++++++++ .../slist/slist_test_copyShallow.wat | 1192 ++++++++ .../slist/slist_test_filter1.wat | 1031 +++++++ .../slist/slist_test_filter2.wat | 1174 +++++++ .../slist/slist_test_filter3.wat | 1242 ++++++++ .../slist/slist_test_filterMut1.wat | 1096 +++++++ .../slist/slist_test_filterMut2.wat | 1239 ++++++++ .../slist/slist_test_filterMut3.wat | 1044 +++++++ .../slist/slist_test_get.wat | 955 ++++++ .../slist/slist_test_getFirst.wat | 836 +++++ .../slist/slist_test_getLast.wat | 836 +++++ .../slist/slist_test_indexOf.wat | 776 +++++ .../slist/slist_test_iterAdd.wat | 1453 +++++++++ .../slist/slist_test_iterRemove.wat | 1395 +++++++++ .../slist/slist_test_new.wat | 648 ++++ .../slist/slist_test_remove.wat | 1330 ++++++++ .../slist/slist_test_removeAll.wat | 912 ++++++ .../slist/slist_test_removeAt.wat | 1179 +++++++ .../slist/slist_test_removeFirst.wat | 1009 ++++++ .../slist/slist_test_removeLast.wat | 1129 +++++++ .../slist/slist_test_replaceAt.wat | 1063 +++++++ .../slist/slist_test_reverse.wat | 963 ++++++ .../slist/slist_test_splice.wat | 1174 +++++++ .../slist/slist_test_spliceAt.wat | 1287 ++++++++ .../slist/slist_test_sublist.wat | 1157 +++++++ .../slist/slist_test_toArray.wat | 1099 +++++++ .../slist/slist_test_zipIterAdd.wat | 1950 ++++++++++++ .../slist/slist_test_zipIterNext.wat | 1254 ++++++++ .../slist/slist_test_zipIterRemove.wat | 1852 +++++++++++ .../slist/slist_test_zipIterReplace.wat | 1704 +++++++++++ .../stack/stack_test_pop.wat | 1413 +++++++++ .../stack/stack_test_push.wat | 1138 +++++++ .../treeset/treeset_test_add.wat | 1603 ++++++++++ .../treeset/treeset_test_iterNext.wat | 1821 +++++++++++ .../treeset/treeset_test_iterRemove.wat | 2683 ++++++++++++++++ .../treeset/treeset_test_remove.wat | 2383 +++++++++++++++ .../treeset/treeset_test_removeAll.wat | 1708 +++++++++++ .../treeset/treeset_test_size.wat | 1382 +++++++++ .../treetable/treetable_test_add.wat | 1491 +++++++++ .../treetable/treetable_test_get.wat | 1585 ++++++++++ .../treetable/treetable_test_getFirst.wat | 1459 +++++++++ .../treetable_test_getGreaterThan.wat | 1707 +++++++++++ .../treetable/treetable_test_getLast.wat | 1459 +++++++++ .../treetable/treetable_test_getLessThan.wat | 1707 +++++++++++ .../treetable/treetable_test_iterNext.wat | 1750 +++++++++++ .../treetable/treetable_test_iterRemove.wat | 2532 +++++++++++++++ .../treetable/treetable_test_remove.wat | 2244 ++++++++++++++ .../treetable/treetable_test_removeAll.wat | 1517 +++++++++ .../treetable/treetable_test_removeFirst.wat | 2268 ++++++++++++++ .../treetable/treetable_test_removeLast.wat | 2309 ++++++++++++++ .../treetable/treetable_test_size.wat | 1343 ++++++++ 159 files changed, 219334 insertions(+) create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat create mode 100644 benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat new file mode 100644 index 000000000..519d36f0a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat @@ -0,0 +1,906 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 0 + i32.const 1036 + call $array_new + i32.store offset=1040 + i32.const 0 + i32.load offset=1040 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat new file mode 100644 index 000000000..9ba6bff92 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat @@ -0,0 +1,1072 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 1032 + call $array_new + drop + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + i32.const 0 + i32.load offset=1032 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 8 + i32.const 0 + i32.load offset=1032 + local.get 0 + i32.const 8 + i32.add + i32.const 1 + call $array_add_at + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1032 + call $array_destroy + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_add_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $array_add + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + br_if 1 (;@3;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + call $expand_capacity + i32.store offset=12 + block ;; label = @3 + local.get 3 + i32.load offset=12 + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=12 + i32.store offset=28 + br 2 (;@1;) + end + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=8 + call $memmove + drop + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1028 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1028 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1028 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1028 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "a\00") + (data (;1;) (i32.const 1028) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat new file mode 100644 index 000000000..c7127a039 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -0,0 +1,991 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + local.get 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_contains + i32.store offset=8 + local.get 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_contains + i32.store offset=4 + local.get 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $array_contains + i32.store + i32.const 2 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat new file mode 100644 index 000000000..59bbf4e82 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat @@ -0,0 +1,1148 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + i32.const 1040 + call $array_copy_deep + drop + i32.const 0 + i32.load offset=1040 + call $array_size + i32.const 0 + i32.load offset=1036 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 2 + call $array_destroy_cb + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_destroy_cb (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + call_indirect (type 2) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + call $array_destroy + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_copy_deep (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 28 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 1) + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 4 + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 0) + local.set 2 + local.get 3 + i32.load offset=12 + local.get 2 + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=24 + call_indirect (type 2) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + f32.load offset=8 + f32.store offset=8 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=24 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=12 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $copy (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + i32.load + i32.store + local.get 1 + i32.load offset=8 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $copy $free $malloc $calloc) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat new file mode 100644 index 000000000..687e14125 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat @@ -0,0 +1,892 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "e\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat new file mode 100644 index 000000000..e0873279c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat @@ -0,0 +1,904 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 12 + i32.add + call $array_index_of + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + call $array_index_of + drop + i32.const 0 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_index_of (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat new file mode 100644 index 000000000..06ae7109b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -0,0 +1,1479 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1040 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=36 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=24 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $array_add + drop + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1040 + call $array_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $array_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 24 + i32.add + call $array_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 3 + local.get 0 + call $array_get_at + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 4 + local.get 0 + call $array_get_at + drop + local.get 0 + i32.load offset=28 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $array_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_add_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $array_add + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + br_if 1 (;@3;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + call $expand_capacity + i32.store offset=12 + block ;; label = @3 + local.get 3 + i32.load offset=12 + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=12 + i32.store offset=28 + br 2 (;@1;) + end + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=8 + call $memmove + drop + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $array_iter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $array_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $array_iter_add (type 0) (param i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.set 1 + local.get 2 + i32.load offset=8 + local.set 0 + local.get 2 + i32.load offset=12 + local.tee 3 + local.get 3 + i32.load offset=4 + local.tee 3 + i32.const 1 + i32.add + i32.store offset=4 + local.get 1 + local.get 0 + local.get 3 + call $array_add_at + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00N\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat new file mode 100644 index 000000000..7d8523702 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -0,0 +1,1342 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=28 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 40 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 28 + i32.add + call $array_add + drop + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=36 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=28 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1036 + call $array_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $array_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + i32.const 0 + call $array_iter_remove + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + i32.store offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + call $memmove + drop + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_iter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $array_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $array_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 7 + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load offset=8 + br_if 0 (;@1;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + call $array_remove_at + i32.store offset=4 + block ;; label = @2 + local.get 2 + i32.load offset=4 + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + end + end + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat new file mode 100644 index 000000000..dedb8b5a6 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -0,0 +1,1271 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1048 + call $array_new + drop + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=52 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=40 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 56 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 52 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 48 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 44 + i32.add + call $array_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1048 + call $array_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + call $array_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=20 + i32.load + local.get 0 + i32.load offset=48 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 16 + i32.add + call $array_iter_replace + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 12 + i32.add + call $array_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 48 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + call $array_destroy + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_replace_at (type 4) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 4 + i32.load offset=20 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $array_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_iter_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $array_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $array_iter_replace (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=4 + call $array_replace_at + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "replacement\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat new file mode 100644 index 000000000..adbaad4b3 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat @@ -0,0 +1,1055 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (param i32 i32 i32))) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $reduce_add (type 3) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=28 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=28 + i32.load + local.set 2 + br 1 (;@1;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + i32.load + local.set 2 + br 1 (;@1;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.add + i32.store) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1040 + call $array_new + drop + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $array_reduce + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $array_reduce + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.add + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $array_reduce + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.add + local.get 0 + i32.load offset=16 + i32.add + local.get 0 + i32.load offset=12 + i32.add + local.get 0 + i32.load offset=8 + i32.add + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_reduce (type 3) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.load + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + i32.load offset=12 + i32.load + i32.const 0 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + call_indirect (type 3) + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.load + i32.const 1 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=12 + i32.load offset=12 + i32.load offset=4 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + call_indirect (type 3) + end + local.get 3 + i32.const 2 + i32.store + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.load offset=12 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + call_indirect (type 3) + local.get 3 + local.get 3 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 16 + i32.add + global.set 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $reduce_add $malloc $calloc $free) + (data (;0;) (i32.const 1024) "e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat new file mode 100644 index 000000000..21ce0a636 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -0,0 +1,1167 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1032 + call $array_new + drop + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.load offset=24 + i32.const 2 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=24 + i32.const 16 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=24 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + i32.const 0 + i32.load offset=1032 + local.get 0 + i32.load offset=8 + call $array_add + drop + local.get 0 + local.get 0 + i32.load offset=20 + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=8 + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1032 + local.get 0 + i32.load offset=16 + i32.const 0 + call $array_remove + drop + i32.const 0 + i32.load offset=1032 + call $array_size + local.get 0 + i32.load offset=24 + i32.lt_u + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1032 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 12 + i32.add + call $array_index_of + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 3 + i32.load offset=12 + i32.sub + i32.const 2 + i32.shl + i32.store offset=4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + call $memmove + drop + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_index_of (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1028 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1028 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1028 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1028 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "n\00") + (data (;1;) (i32.const 1028) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat new file mode 100644 index 000000000..dc5ba7e9e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -0,0 +1,864 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1032 + call $array_new + drop + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.load offset=24 + i32.const 2 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=24 + i32.const 16 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=24 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + i32.const 0 + i32.load offset=1032 + local.get 0 + i32.load offset=8 + call $array_add + drop + local.get 0 + local.get 0 + i32.load offset=20 + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=8 + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1032 + call $array_remove_all + i32.const 0 + i32.load offset=1032 + call $array_size + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1032 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove_all (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1028 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1028 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1028 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1028 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1028 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "n\00") + (data (;1;) (i32.const 1028) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat new file mode 100644 index 000000000..59c0b4252 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat @@ -0,0 +1,1137 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + i32.const 0 + call $array_remove_at + drop + i32.const 3 + i32.const 0 + i32.load offset=1036 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 12 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + i32.store offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + call $memmove + drop + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "e\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat new file mode 100644 index 000000000..8f6028243 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat @@ -0,0 +1,960 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + i32.const 2 + i32.const 0 + call $array_replace_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_replace_at (type 4) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 4 + i32.load offset=20 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $array_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "r\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat new file mode 100644 index 000000000..1cf7dd4f9 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat @@ -0,0 +1,990 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + call $array_reverse + i32.const 0 + i32.load offset=1036 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_reverse (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 1 + i32.sub + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + i32.load + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 1 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + local.get 1 + i32.load + i32.store + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const -1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat new file mode 100644 index 000000000..d2d722164 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat @@ -0,0 +1,1033 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + i32.const 1036 + call $array_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 1040 + call $array_copy_shallow + drop + i32.const 0 + i32.load offset=1040 + call $array_size + i32.const 0 + i32.load offset=1036 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $array_get_at + drop + i32.const 0 + i32.load offset=1040 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $array_destroy + i32.const 0 + i32.load offset=1036 + call $array_destroy + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_copy_shallow (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 28 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 4 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call_indirect (type 0) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=12 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + f32.load offset=8 + f32.store offset=8 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=24 + i32.store offset=24 + local.get 2 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat new file mode 100644 index 000000000..ce51cb260 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat @@ -0,0 +1,1120 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1040 + call $array_new + drop + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=24 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1040 + i32.const 1 + i32.const 3 + local.get 0 + i32.const 20 + i32.add + call $array_subarray + drop + i32.const 3 + local.get 0 + i32.load offset=20 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + i32.const 0 + local.get 0 + i32.const 16 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=20 + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $array_get_at + drop + local.get 0 + i32.load offset=20 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $array_get_at + drop + local.get 0 + i32.const 36 + i32.add + local.get 0 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + call $array_destroy + i32.const 0 + i32.load offset=1040 + call $array_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_subarray (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=16 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 4 + i32.const 3 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.const 1 + i32.const 28 + local.get 4 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @2 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 4 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 4 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 1) + local.set 3 + local.get 4 + i32.load offset=8 + local.get 3 + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=24 + i32.load offset=24 + call_indirect (type 2) + local.get 4 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=24 + i32.load offset=24 + i32.store offset=24 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + i32.store + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=8 + i32.load + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 4 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28 + local.set 3 + local.get 4 + i32.const 32 + i32.add + global.set 0 + local.get 3) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat new file mode 100644 index 000000000..9ef31665b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -0,0 +1,1961 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 112 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=108 + i32.const 1048 + call $array_new + drop + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=104 + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=96 + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 94 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 94 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 102 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 78 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.const 94 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 46 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 46 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.const 46 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.const 46 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.const 70 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.const 54 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.const 62 + i32.add + call $strcmp + i32.const 0 + i32.eq + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 102 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 94 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 86 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 78 + i32.add + call $array_add + drop + i32.const 1052 + call $array_new + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 70 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 62 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 54 + i32.add + call $array_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1052 + call $array_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $array_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 94 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 46 + i32.add + local.get 0 + i32.const 38 + i32.add + call $array_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + local.get 0 + i32.const 4 + i32.add + call $array_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.const 4 + i32.add + call $array_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 4 + i32.add + call $array_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 38 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 5 + i32.const 0 + i32.load offset=1048 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 4 + i32.const 0 + i32.load offset=1052 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + call $array_destroy + i32.const 0 + i32.load offset=1048 + call $array_destroy + local.get 0 + i32.const 112 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_add_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $array_add + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + br_if 1 (;@3;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + call $expand_capacity + i32.store offset=12 + block ;; label = @3 + local.get 3 + i32.load offset=12 + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=12 + i32.store offset=28 + br 2 (;@1;) + end + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=8 + call $memmove + drop + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_index_of (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $array_zip_iter_init (type 5) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $array_zip_iter_next (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_zip_iter_add (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + local.tee 2 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=8 + call $expand_capacity + br_if 1 (;@3;) + end + local.get 3 + i32.load offset=4 + i32.load + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=4 + call $expand_capacity + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + call $array_add_at + drop + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + call $array_add_at + drop + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat new file mode 100644 index 000000000..3b3d0303a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat @@ -0,0 +1,1229 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + i32.const 1044 + call $array_new + drop + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 70 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 62 + i32.add + call $array_add + drop + i32.const 1048 + call $array_new + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 38 + i32.add + call $array_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $array_zip_iter_init + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $array_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + br_if 0 (;@3;) + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=4 + call $CHECK_EQUAL_C_STRING + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.const 2 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.load offset=4 + call $CHECK_EQUAL_C_STRING + end + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + call $array_destroy + i32.const 0 + i32.load offset=1044 + call $array_destroy + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_zip_iter_init (type 4) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $array_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $CHECK_EQUAL_C_STRING (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat new file mode 100644 index 000000000..50d1f98dc --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -0,0 +1,1696 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32))) + (type (;6;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + i32.const 1044 + call $array_new + drop + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 78 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.const 78 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 78 + i32.add + call $strcmp + i32.const 0 + i32.eq + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 70 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 62 + i32.add + call $array_add + drop + i32.const 1048 + call $array_new + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 38 + i32.add + call $array_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $array_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $array_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 78 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 4 + i32.add + local.get 0 + call $array_zip_iter_remove + drop + end + br 0 (;@2;) + end + end + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.load offset=4 + call $CHECK_EQUAL_C_STRING + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + i32.const 0 + i32.load offset=1048 + call $array_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + call $array_destroy + i32.const 0 + i32.load offset=1044 + call $array_destroy + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove_at (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + i32.store offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + call $memmove + drop + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $array_zip_iter_init (type 5) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $array_zip_iter_next (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_zip_iter_remove (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=4 + call $array_remove_at + drop + local.get 3 + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load + call $array_remove_at + drop + local.get 3 + i32.load offset=8 + i32.const 1 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.const 7 + i32.store offset=12 + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 4) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $CHECK_EQUAL_C_STRING (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat new file mode 100644 index 000000000..210d08e0c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -0,0 +1,1712 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32 i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 128 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=124 + i32.const 1048 + call $array_new + drop + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=120 + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=112 + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 118 + i32.add + local.get 0 + i32.const 110 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 110 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 118 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 94 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.const 110 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 118 + i32.add + local.get 0 + i32.const 62 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.const 62 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.const 62 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 110 + i32.add + local.get 0 + i32.const 62 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 86 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 70 + i32.add + call $strcmp + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 78 + i32.add + call $strcmp + i32.const 0 + i32.eq + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 118 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 110 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 102 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 94 + i32.add + call $array_add + drop + i32.const 1052 + call $array_new + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 86 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + call $array_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 70 + i32.add + call $array_add + drop + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1052 + call $array_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.const 24 + i32.add + call $array_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + local.get 0 + i32.const 110 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $array_zip_iter_replace + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 12 + i32.add + call $array_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 12 + i32.add + call $array_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 54 + i32.add + call $array_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + call $array_destroy + i32.const 0 + i32.load offset=1048 + call $array_destroy + local.get 0 + i32.const 128 + i32.add + global.set 0 + i32.const 0) + (func $array_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $array_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $array_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_replace_at (type 4) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + local.get 4 + i32.load offset=24 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 4 + i32.load offset=20 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $array_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $array_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=12 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=4) + (func $array_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $array_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_zip_iter_replace (type 7) (param i32 i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 5 + global.set 0 + local.get 5 + local.get 0 + i32.store offset=24 + local.get 5 + local.get 1 + i32.store offset=20 + local.get 5 + local.get 2 + i32.store offset=16 + local.get 5 + local.get 3 + i32.store offset=12 + local.get 5 + local.get 4 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=24 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 5 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 5 + i32.load offset=24 + i32.load + local.get 5 + i32.load offset=20 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=12 + call $array_replace_at + drop + local.get 5 + i32.load offset=24 + i32.load offset=4 + local.get 5 + i32.load offset=16 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=8 + call $array_replace_at + drop + local.get 5 + i32.const 0 + i32.store offset=28 + end + local.get 5 + i32.load offset=28 + local.set 4 + local.get 5 + i32.const 32 + i32.add + global.set 0 + local.get 4) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat new file mode 100644 index 000000000..e73671fbf --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat @@ -0,0 +1,1751 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 28 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 16 + i32.add + i32.const 4 + call $deque_add_at + drop + local.get 0 + i32.const 0 + i32.load offset=1044 + call $deque_get_buffer + i32.store offset=12 + local.get 0 + i32.load offset=12 + i32.load offset=16 + local.get 0 + i32.const 16 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load offset=20 + local.get 0 + i32.const 24 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.load offset=24 + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 20 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat new file mode 100644 index 000000000..369c1f9bc --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat @@ -0,0 +1,1773 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + i32.const 1 + call $deque_add_at + drop + local.get 0 + i32.const 0 + i32.load offset=1044 + call $deque_get_buffer + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=20 + i32.store offset=24 + local.get 0 + i32.load offset=24 + local.get 0 + i32.const 32 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 56 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=28 + i32.store offset=16 + local.get 0 + i32.load offset=16 + local.get 0 + i32.const 48 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=12 + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 36 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat new file mode 100644 index 000000000..c21a02130 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat @@ -0,0 +1,1773 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + i32.const 3 + call $deque_add_at + drop + local.get 0 + i32.const 0 + i32.load offset=1044 + call $deque_get_buffer + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=24 + i32.store offset=24 + local.get 0 + i32.load offset=24 + local.get 0 + i32.const 32 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 52 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=28 + i32.store offset=16 + local.get 0 + i32.load offset=16 + local.get 0 + i32.const 48 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=4 + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 56 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat new file mode 100644 index 000000000..4c5523bc5 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat @@ -0,0 +1,1773 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + i32.const 1 + call $deque_add_at + drop + local.get 0 + i32.const 0 + i32.load offset=1044 + call $deque_get_buffer + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.load + i32.load + i32.store offset=24 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=16 + i32.load + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=40 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=28 + i32.load + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=56 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat new file mode 100644 index 000000000..3950bea5d --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat @@ -0,0 +1,1773 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + i32.const 1 + call $deque_add_at + drop + local.get 0 + i32.const 0 + i32.load offset=1044 + call $deque_get_buffer + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=28 + i32.load + i32.store offset=24 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=56 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load + i32.load + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=52 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=20 + i32.load + i32.store offset=16 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=4 + i32.load + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat new file mode 100644 index 000000000..99c8ffd2b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat @@ -0,0 +1,1112 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_first + drop + i32.const 3 + i32.const 0 + i32.load offset=1036 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.load offset=1036 + call $deque_capacity + i32.store offset=12 + local.get 0 + i32.const 0 + i32.load offset=1036 + call $deque_get_buffer + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 24 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.const 2 + i32.sub + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 20 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.const 3 + i32.sub + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 16 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat new file mode 100644 index 000000000..d0c3f7560 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat @@ -0,0 +1,1075 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 3 + i32.const 0 + i32.load offset=1036 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.load offset=1036 + call $deque_get_buffer + i32.store offset=12 + local.get 0 + local.get 0 + i32.load offset=12 + i32.load + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 24 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.load offset=4 + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 20 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 16 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat new file mode 100644 index 000000000..29cab93d3 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat @@ -0,0 +1,1227 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 1040 + call $deque_conf_init + i32.const 0 + i32.const 4 + i32.store offset=1040 + i32.const 1040 + i32.const 1056 + call $deque_new_conf + drop) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1056 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=36 + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 56 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 52 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 48 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 44 + i32.add + call $deque_add_last + drop + local.get 0 + i32.const 0 + i32.load offset=1056 + call $deque_capacity + i32.store offset=32 + i32.const 4 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 40 + i32.add + call $deque_add_first + drop + local.get 0 + i32.const 0 + i32.load offset=1056 + call $deque_capacity + i32.store offset=32 + i32.const 8 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.load offset=1056 + call $deque_get_buffer + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.load + i32.load + i32.store offset=24 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=48 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=4 + i32.load + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=56 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=8 + i32.load + i32.store offset=16 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=52 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=44 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=28 + i32.load + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=40 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + local.get 0 + local.get 0 + i32.load offset=28 + i32.load offset=16 + i32.load + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66608)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) "0\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat new file mode 100644 index 000000000..af7336649 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat @@ -0,0 +1,1064 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 24 + i32.add + call $deque_conf_init + local.get 0 + i32.const 2 + i32.store offset=24 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + call $deque_new_conf + drop + i32.const 2 + local.get 0 + i32.load offset=20 + call $deque_capacity + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 12 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 8 + i32.add + call $deque_add + drop + i32.const 4 + local.get 0 + i32.load offset=20 + call $deque_capacity + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat new file mode 100644 index 000000000..0fbf07fe1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat @@ -0,0 +1,1175 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 4 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 2 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 24 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=8 + local.get 2 + i32.load offset=20 + i32.add + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=28 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=16) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat new file mode 100644 index 000000000..d52577f9a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat @@ -0,0 +1,1478 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (type (;7;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 4 + call $malloc + i32.store offset=40 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=36 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=28 + i32.store + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=24 + i32.store + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=20 + i32.store + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.load offset=40 + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.load offset=36 + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.load offset=32 + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + local.get 0 + i32.const 16 + i32.add + call $deque_copy_deep + drop + local.get 0 + local.get 0 + i32.load offset=16 + call $deque_size + i32.store offset=12 + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=16 + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=16 + i32.const 2 + local.get 0 + call $deque_get_at + drop + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + i32.const 2 + call $deque_destroy_cb + local.get 0 + i32.load offset=40 + free + local.get 0 + i32.load offset=36 + free + local.get 0 + i32.load offset=32 + free + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_destroy_cb (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_remove_all_cb + local.get 2 + i32.load offset=12 + call $deque_destroy + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $deque_remove_all_cb (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_foreach + local.get 2 + i32.load offset=12 + call $deque_remove_all + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $deque_foreach (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=8 + call_indirect (type 2) + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $deque_remove_all (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 7) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_copy_deep (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 32 + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=12 + local.get 2 + i32.store offset=16 + block ;; label = @2 + local.get 2 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=28 + call_indirect (type 2) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=24 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=28 + i32.store offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.load offset=16 + local.get 3 + i32.load offset=20 + call $copy_buffer + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $copy (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + i32.load + i32.store + local.get 1 + i32.load offset=8 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $copy $free $malloc $calloc) + (data (;0;) (i32.const 1024) "z\00y\00x\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat new file mode 100644 index 000000000..cbf0b14a7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat @@ -0,0 +1,1275 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 28 + i32.add + call $deque_copy_shallow + drop + local.get 0 + local.get 0 + i32.load offset=28 + call $deque_size + i32.store offset=24 + i32.const 3 + local.get 0 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=28 + i32.const 0 + local.get 0 + i32.const 20 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=28 + i32.const 1 + local.get 0 + i32.const 16 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=28 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=20 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=16 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=28 + call $deque_destroy + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_copy_shallow (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call_indirect (type 1) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=20 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=24 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=28 + i32.store offset=28 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.load offset=16 + i32.const 0 + call $copy_buffer + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + local.get 2 + i32.load + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat new file mode 100644 index 000000000..11459d9b7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -0,0 +1,1349 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred1 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.le_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 28 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 40 + i32.add + call $pred1 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 36 + i32.add + call $pred1 + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.const 32 + i32.add + call $pred1 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=16 + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 16 + i32.add + call $deque_filter + drop + i32.const 3 + local.get 0 + i32.load offset=16 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=16 + call $deque_get_buffer + i32.store offset=12 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.const 40 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load offset=4 + local.get 0 + i32.const 36 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 32 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + free + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $deque_filter (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.const 8 + i32.add + call $deque_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + call $deque_add + drop + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred1 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat new file mode 100644 index 000000000..59b972bad --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -0,0 +1,1348 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred2 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.gt_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 28 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 40 + i32.add + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 36 + i32.add + call $pred2 + br_if 0 (;@1;) + local.get 0 + i32.const 32 + i32.add + call $pred2 + i32.const 0 + i32.ne + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=16 + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 16 + i32.add + call $deque_filter + drop + local.get 0 + local.get 0 + i32.load offset=16 + call $deque_get_buffer + i32.store offset=12 + i32.const 3 + local.get 0 + i32.load offset=16 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.const 28 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load offset=4 + local.get 0 + i32.const 24 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load offset=8 + local.get 0 + i32.const 20 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + free + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $deque_filter (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.const 8 + i32.add + call $deque_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + call $deque_add + drop + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred2 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat new file mode 100644 index 000000000..1dad6264a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -0,0 +1,1326 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred3 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 5 + i32.gt_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 28 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 40 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 36 + i32.add + call $pred3 + br_if 0 (;@1;) + local.get 0 + i32.const 32 + i32.add + call $pred3 + i32.const 0 + i32.ne + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=16 + i32.const 0 + i32.load offset=1040 + i32.const 1 + local.get 0 + i32.const 16 + i32.add + call $deque_filter + drop + local.get 0 + local.get 0 + i32.load offset=16 + call $deque_get_buffer + i32.store offset=12 + i32.const 1 + local.get 0 + i32.load offset=16 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.const 20 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=16 + free + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_get_buffer (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16) + (func $deque_filter (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.const 8 + i32.add + call $deque_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + call $deque_add + drop + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred3 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat new file mode 100644 index 000000000..60374b01f --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -0,0 +1,1968 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred1 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.le_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=4 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 12 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 8 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 4 + i32.add + call $pred1 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred1 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred1 + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.const 16 + i32.add + call $pred1 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 1 + call $deque_filter_mut + drop + i32.const 3 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=36 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + block ;; label = @6 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=32 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + call $deque_size + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.add + local.get 2 + i32.load offset=12 + i32.and + i32.store offset=8 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.const 0 + call $deque_remove_at + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred1 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat new file mode 100644 index 000000000..426c59ab1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -0,0 +1,1971 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred2 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.gt_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=4 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 12 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 8 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 4 + i32.add + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred2 + br_if 0 (;@1;) + local.get 0 + i32.const 16 + i32.add + call $pred2 + i32.const 0 + i32.ne + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 1 + call $deque_filter_mut + drop + i32.const 3 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=36 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + block ;; label = @6 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=32 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + call $deque_size + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.add + local.get 2 + i32.load offset=12 + i32.and + i32.store offset=8 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.const 0 + call $deque_remove_at + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred2 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat new file mode 100644 index 000000000..4fce44482 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -0,0 +1,1941 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $pred3 (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 5 + i32.gt_s + i32.const 1 + i32.and) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=4 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.const 12 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 8 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 4 + i32.add + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 24 + i32.add + call $pred3 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.const 20 + i32.add + call $pred3 + br_if 0 (;@1;) + local.get 0 + i32.const 16 + i32.add + call $pred3 + i32.const 0 + i32.ne + i32.const -1 + i32.xor + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $deque_add_last + drop + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + i32.const 1 + call $deque_filter_mut + drop + i32.const 1 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store + i32.const 0 + i32.load offset=1040 + local.get 0 + call $deque_remove_first + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=36 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + block ;; label = @6 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=32 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $deque_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + call $deque_size + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.add + local.get 2 + i32.load offset=12 + i32.and + i32.store offset=8 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.const 0 + call $deque_remove_at + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred3 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat new file mode 100644 index 000000000..91b11eed4 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat @@ -0,0 +1,1118 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $deque_get_at + drop + local.get 0 + i32.const 0 + i32.load offset=1036 + i32.const 42 + local.get 0 + i32.const 8 + i32.add + call $deque_get_at + i32.store offset=4 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 8 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat new file mode 100644 index 000000000..b7eb36640 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat @@ -0,0 +1,1137 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_get_first + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat new file mode 100644 index 000000000..82355936f --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat @@ -0,0 +1,1149 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_get_last + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat new file mode 100644 index 000000000..083c805dc --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -0,0 +1,2154 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $deque_add + drop + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=52 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=48 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=36 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + call $deque_iter_init + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 6 + i32.const 0 + i32.load offset=1044 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + call $deque_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=44 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 32 + i32.add + call $deque_iter_add + drop + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.const 3 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 16 + i32.add + call $deque_iter_index + i32.const 1 + i32.sub + i32.eq + i32.const 1 + i32.and + sym_assert + end + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 7 + i32.const 0 + i32.load offset=1044 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 4 + local.get 0 + i32.const 4 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $deque_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.add + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=24 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_iter_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $deque_add_at + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=4 + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_iter_index (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.const 1 + i32.sub) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat new file mode 100644 index 000000000..b444c1e12 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -0,0 +1,1373 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=36 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 56 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 52 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 48 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 44 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $deque_add + drop + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=52 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=48 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=36 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1040 + call $deque_iter_init + local.get 0 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 16 + i32.add + call $deque_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 12 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + sym_assert + br 0 (;@2;) + end + end + call $teardown_tests + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $deque_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.add + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=24 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat new file mode 100644 index 000000000..67810ef64 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -0,0 +1,2142 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1040 + call $deque_new + i32.store offset=1044) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=36 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=32 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=24 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=20 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1040 + call $deque_iter_init + local.get 0 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + call $deque_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.const 3 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 8 + i32.add + i32.const 0 + call $deque_iter_remove + drop + end + block ;; label = @3 + block ;; label = @4 + local.get 0 + i32.load offset=4 + i32.const 2 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + br 1 (;@3;) + end + i32.const 6 + i32.const 0 + i32.load offset=1040 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.const 3 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.load offset=4 + i32.const 1 + i32.sub + local.get 0 + i32.const 8 + i32.add + call $deque_iter_index + i32.eq + i32.const 1 + i32.and + sym_assert + end + local.get 0 + local.get 0 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=36 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + block ;; label = @6 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=32 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $deque_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.add + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=24 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.const 16 + i32.add + call $deque_remove_at + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + br_if 0 (;@2;) + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const -1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.store offset=8 + block ;; label = @3 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + end + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $deque_iter_index (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.const 1 + i32.sub) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat new file mode 100644 index 000000000..ee5e4f928 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat @@ -0,0 +1,1188 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + call $deque_remove_all + local.get 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_get_first + i32.store offset=8 + local.get 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $deque_get_last + i32.store + i32.const 8 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 8 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_remove_all (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat new file mode 100644 index 000000000..ec25a451e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat @@ -0,0 +1,1257 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $deque_get_first + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $deque_remove_first + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $deque_get_first + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat new file mode 100644 index 000000000..0834b9f36 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat @@ -0,0 +1,1272 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add_first + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_add_last + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $deque_get_last + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $deque_remove_last + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $deque_get_last + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat new file mode 100644 index 000000000..1a4d9e6e7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat @@ -0,0 +1,1263 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + call $deque_reverse + i32.const 0 + i32.load offset=1036 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $deque_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $deque_get_at + drop + i32.const 0 + i32.load offset=1036 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $deque_get_at + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=20 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_reverse (type 2) (param i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=44 + local.get 1 + local.get 1 + i32.load offset=44 + i32.load + i32.store offset=32 + local.get 1 + local.get 1 + i32.load offset=44 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 1 + local.get 1 + i32.load offset=44 + i32.load offset=8 + i32.store offset=24 + local.get 1 + i32.const 0 + i32.store offset=40 + local.get 1 + local.get 1 + i32.load offset=32 + i32.const 1 + i32.sub + i32.store offset=36 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=40 + local.get 1 + i32.load offset=32 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 1 + local.get 1 + i32.load offset=24 + local.get 1 + i32.load offset=40 + i32.add + local.get 1 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 1 + local.get 1 + i32.load offset=24 + local.get 1 + i32.load offset=36 + i32.add + local.get 1 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 1 + local.get 1 + i32.load offset=44 + i32.load offset=16 + local.get 1 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=44 + i32.load offset=16 + local.get 1 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 1 + i32.load offset=44 + i32.load offset=16 + local.get 1 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 1 + i32.load offset=44 + i32.load offset=16 + local.get 1 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 1 + i32.load offset=12 + i32.store + local.get 1 + local.get 1 + i32.load offset=40 + i32.const 1 + i32.add + i32.store offset=40 + local.get 1 + local.get 1 + i32.load offset=36 + i32.const -1 + i32.add + i32.store offset=36 + br 0 (;@2;) + end + end) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat new file mode 100644 index 000000000..5232375e6 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat @@ -0,0 +1,1056 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $deque_add + drop + local.get 0 + i32.const 0 + i32.load offset=1036 + call $deque_size + i32.store offset=8 + i32.const 4 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat new file mode 100644 index 000000000..8ce28f5d9 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat @@ -0,0 +1,1169 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1036 + call $deque_new + i32.store offset=1040) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $deque_add + drop + i32.const 8 + i32.const 0 + i32.load offset=1036 + call $deque_capacity + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + call $deque_trim_capacity + drop + i32.const 4 + i32.const 0 + i32.load offset=1036 + call $deque_capacity + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_trim_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load + call $upper_pow_two + i32.store offset=4 + block ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=20 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat new file mode 100644 index 000000000..a1d6074c0 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -0,0 +1,2706 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 112 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=108 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=80 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 102 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $deque_add + drop + local.get 0 + i32.const 48 + i32.add + call $deque_new + drop + local.get 0 + i32.load offset=48 + local.get 0 + i32.const 70 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=48 + local.get 0 + i32.const 62 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=48 + local.get 0 + i32.const 54 + i32.add + call $deque_add + drop + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store8 offset=34 + local.get 0 + i32.const 0 + i32.store8 offset=35 + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=48 + call $deque_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $deque_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 94 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 42 + i32.add + local.get 0 + i32.const 34 + i32.add + call $deque_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 42 + i32.add + local.get 0 + i32.const 4 + i32.add + call $deque_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 34 + i32.add + local.get 0 + i32.const 4 + i32.add + call $deque_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 4 + i32.add + call $deque_index_of + drop + i32.const 3 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 42 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=48 + local.get 0 + i32.const 34 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 5 + i32.const 0 + i32.load offset=1044 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 4 + local.get 0 + i32.load offset=48 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=48 + call $deque_destroy + call $teardown_tests + local.get 0 + i32.const 112 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=40 + i32.load offset=4 + local.get 3 + i32.load offset=40 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=40 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=32 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=32 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=36 + call $deque_add_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + br_if 0 (;@6;) + local.get 3 + i32.load offset=20 + br_if 1 (;@5;) + end + block ;; label = @6 + block ;; label = @7 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@7;) + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 1 + i32.add + local.set 2 + br 1 (;@6;) + end + i32.const 0 + local.set 2 + end + local.get 3 + local.get 2 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=16 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @6 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=32 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 1 + i32.add + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load + local.get 3 + i32.load offset=32 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=8 + local.get 2 + i32.load offset=20 + i32.add + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=28 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=16) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $deque_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=16 + i32.and + i32.store + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=16 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=40 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44) + (func $deque_zip_iter_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.load + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.load offset=4 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=8 + call $deque_add_at + drop + local.get 3 + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=8 + call $deque_add_at + drop + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00X\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat new file mode 100644 index 000000000..eeeeb3367 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -0,0 +1,1587 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 70 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 62 + i32.add + call $deque_add + drop + local.get 0 + i32.const 32 + i32.add + call $deque_new + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 54 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 46 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 38 + i32.add + call $deque_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=32 + call $deque_zip_iter_init + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $deque_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + br_if 0 (;@3;) + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=4 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.const 2 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.load offset=4 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + end + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=32 + call $deque_destroy + call $teardown_tests + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $deque_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=16 + i32.and + i32.store + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=16 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=40 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat new file mode 100644 index 000000000..730293d77 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -0,0 +1,2574 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.load offset=48 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=48 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.load offset=40 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=40 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 70 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 62 + i32.add + call $deque_add + drop + local.get 0 + i32.const 32 + i32.add + call $deque_new + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 54 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 46 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=32 + local.get 0 + i32.const 38 + i32.add + call $deque_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=32 + call $deque_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $deque_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 78 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 4 + i32.add + local.get 0 + call $deque_zip_iter_remove + drop + end + br 0 (;@2;) + end + end + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.load offset=4 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 46 + i32.add + local.get 0 + i32.load + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 46 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=32 + call $deque_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=32 + call $deque_destroy + call $teardown_tests + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=36 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_first + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + call $deque_remove_last + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.const 1 + i32.shr_u + i32.const 1 + i32.sub + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + block ;; label = @6 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @6 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@6;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=36 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.const 1 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.load + i32.store offset=4 + block ;; label = @5 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + block ;; label = @5 + local.get 3 + i32.load offset=16 + i32.eqz + br_if 0 (;@5;) + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.const 4 + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@3;) + end + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=40 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.sub + i32.const 2 + i32.shl + call $memmove + drop + end + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=12 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=32 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $deque_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=8 + local.get 2 + i32.load offset=20 + i32.add + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=28 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=16) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $deque_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $deque_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=16 + i32.and + i32.store + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=16 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=40 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44) + (func $deque_zip_iter_remove (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=8 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load offset=4 + call $deque_remove_at + drop + local.get 3 + i32.load offset=8 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 3 + i32.load + call $deque_remove_at + drop + local.get 3 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat new file mode 100644 index 000000000..fe7d0fdd4 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -0,0 +1,2065 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32 i32 i32) (result i32))) + (type (;8;) (func (param i32 i32 i32 i32 i32) (result i32))) + (func $setup_tests (type 3) + i32.const 0 + i32.const 1044 + call $deque_new + i32.store offset=1048) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1044 + call $deque_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 128 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=124 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=96 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 118 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 110 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 102 + i32.add + call $deque_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $deque_add + drop + local.get 0 + i32.const 64 + i32.add + call $deque_new + drop + local.get 0 + i32.load offset=64 + local.get 0 + i32.const 86 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=64 + local.get 0 + i32.const 78 + i32.add + call $deque_add + drop + local.get 0 + i32.load offset=64 + local.get 0 + i32.const 70 + i32.add + call $deque_add + drop + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=60 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store8 offset=58 + local.get 0 + i32.const 0 + i32.store8 offset=59 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=52 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store8 offset=50 + local.get 0 + i32.const 0 + i32.store8 offset=51 + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=64 + call $deque_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.const 24 + i32.add + call $deque_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + local.get 0 + i32.const 110 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 58 + i32.add + local.get 0 + i32.const 50 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $deque_zip_iter_replace + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 58 + i32.add + local.get 0 + i32.const 12 + i32.add + call $deque_index_of + drop + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 50 + i32.add + local.get 0 + i32.const 12 + i32.add + call $deque_index_of + drop + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 58 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=64 + local.get 0 + i32.const 50 + i32.add + call $deque_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=64 + call $deque_destroy + call $teardown_tests + local.get 0 + i32.const 128 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $deque_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $deque_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $deque_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $deque_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_replace_at (type 7) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=24 + i32.load offset=8 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.load offset=16 + local.get 4 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + local.get 4 + i32.load offset=24 + i32.load offset=16 + local.get 4 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 4 + i32.load offset=20 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $deque_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + block ;; label = @4 + local.get 3 + i32.load offset=24 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $deque_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=8 + local.get 2 + i32.load offset=20 + i32.add + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=28 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=16) + (func $deque_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $deque_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=16 + i32.and + i32.store + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=16 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=40 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44) + (func $deque_zip_iter_replace (type 8) (param i32 i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 5 + global.set 0 + local.get 5 + local.get 0 + i32.store offset=24 + local.get 5 + local.get 1 + i32.store offset=20 + local.get 5 + local.get 2 + i32.store offset=16 + local.get 5 + local.get 3 + i32.store offset=12 + local.get 5 + local.get 4 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=24 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 5 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 5 + i32.load offset=24 + i32.load + local.get 5 + i32.load offset=20 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=12 + call $deque_replace_at + drop + local.get 5 + i32.load offset=24 + i32.load offset=4 + local.get 5 + i32.load offset=16 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 5 + i32.load offset=8 + call $deque_replace_at + drop + local.get 5 + i32.const 0 + i32.store offset=28 + end + local.get 5 + i32.load offset=28 + local.set 4 + local.get 5 + i32.const 32 + i32.add + global.set 0 + local.get 4) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00X\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat new file mode 100644 index 000000000..1d674eb05 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat @@ -0,0 +1,926 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1036 + call $list_new + drop + i32.const 1040 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1036 + call $list_destroy + i32.const 0 + i32.load offset=1040 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store8 offset=34 + local.get 0 + i32.const 0 + i32.store8 offset=35 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 42 + i32.add + call $list_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 34 + i32.add + call $list_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 26 + i32.add + call $list_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 18 + i32.add + call $list_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat new file mode 100644 index 000000000..b58c1873c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat @@ -0,0 +1,1701 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1044 + call $list_add_all + drop + i32.const 8 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_add_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $add_all_to_empty + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load + call $list_add_all_at + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $add_all_to_empty (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.const 16 + i32.add + local.get 2 + i32.const 12 + i32.add + call $link_all_externally + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=20 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add_all_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 12 + i32.add + local.get 3 + i32.const 8 + i32.add + call $link_all_externally + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 4 + i32.add + call $get_node_at + drop + local.get 3 + i32.const 0 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.load offset=8 + i32.store + br 1 (;@2;) + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.sub + local.get 3 + call $get_node_at + drop + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.store offset=4 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=8 + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.store offset=8 + end + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + local.get 3 + i32.load offset=20 + i32.load + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $link_all_externally (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.const 1 + i32.const 12 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@5;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.load + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=20 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load + i32.store + br 0 (;@6;) + end + end + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.load + i32.store + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=16 + i32.load + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=16 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.const 1 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat new file mode 100644 index 000000000..9636ca2da --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat @@ -0,0 +1,1652 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + i32.const 2 + call $list_add_all_at + drop + i32.const 4 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1044 + i32.const 4 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1048 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_add_all_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 12 + i32.add + local.get 3 + i32.const 8 + i32.add + call $link_all_externally + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 4 + i32.add + call $get_node_at + drop + local.get 3 + i32.const 0 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.load offset=8 + i32.store + br 1 (;@2;) + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.sub + local.get 3 + call $get_node_at + drop + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.store offset=4 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=8 + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.store offset=8 + end + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + local.get 3 + i32.load offset=20 + i32.load + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $link_all_externally (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.const 1 + i32.const 12 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@5;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.load + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=20 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load + i32.store + br 0 (;@6;) + end + end + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.load + i32.store + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=16 + i32.load + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=16 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.const 1 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat new file mode 100644 index 000000000..c86dc5bae --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat @@ -0,0 +1,1425 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $list_new + drop + i32.const 1052 + call $list_new + drop + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1052 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + i32.const 3 + call $list_add_at + drop + i32.const 5 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 3 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 1 + i32.const 12 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=4 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + call $link_behind + block ;; label = @2 + local.get 3 + i32.load offset=16 + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=4 + i32.store offset=4 + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $link_behind (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + end) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat new file mode 100644 index 000000000..4e6f36e3c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat @@ -0,0 +1,924 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1040 + call $list_new + drop + i32.const 1044 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $list_destroy + i32.const 0 + i32.load offset=1044 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $list_add + drop + i32.const 4 + i32.const 0 + i32.load offset=1040 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $list_add_last + drop + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "p\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat new file mode 100644 index 000000000..2c601e919 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat @@ -0,0 +1,889 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1040 + call $list_new + drop + i32.const 1044 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $list_destroy + i32.const 0 + i32.load offset=1044 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 28 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $list_add + drop + i32.const 4 + i32.const 0 + i32.load offset=1040 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $list_add_last + drop + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "p\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat new file mode 100644 index 000000000..df5c0582d --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -0,0 +1,1008 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1040 + call $list_new + drop + i32.const 1044 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $list_destroy + i32.const 0 + i32.load offset=1044 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=8 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $list_add + drop + i32.const 2 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=28 + local.set 1 + local.get 0 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat new file mode 100644 index 000000000..07407781e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat @@ -0,0 +1,1416 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $list_copy_deep + drop + i32.const 4 + local.get 0 + i32.load offset=12 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.const 1 + call $list_destroy_cb + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_copy_deep (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=16 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=20 + i32.store offset=24 + local.get 3 + local.get 3 + i32.const 16 + i32.add + local.get 3 + i32.const 12 + i32.add + call $list_new_conf + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.store offset=4 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load + local.get 3 + i32.load offset=36 + call_indirect (type 2) + call $list_add + i32.store offset=8 + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + call $list_destroy + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=44 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $copy (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + i32.load + i32.store + local.get 1 + i32.load offset=8 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $copy $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat new file mode 100644 index 000000000..d33a4f7d7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat @@ -0,0 +1,1383 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 24 + i32.add + call $list_copy_shallow + drop + i32.const 4 + local.get 0 + i32.load offset=24 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 20 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 16 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.load offset=28 + local.set 1 + local.get 0 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_copy_shallow (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=40 + local.get 2 + local.get 1 + i32.store offset=36 + local.get 2 + local.get 2 + i32.load offset=40 + i32.load offset=12 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=40 + i32.load offset=16 + i32.store offset=28 + local.get 2 + local.get 2 + i32.load offset=40 + i32.load offset=20 + i32.store offset=32 + local.get 2 + local.get 2 + i32.const 24 + i32.add + local.get 2 + i32.const 20 + i32.add + call $list_new_conf + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=44 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=40 + i32.load offset=4 + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=36 + local.get 2 + i32.load offset=20 + i32.store + local.get 2 + i32.const 0 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load + call $list_add + i32.store offset=16 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + call $list_destroy + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=44 + br 3 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=36 + local.get 2 + i32.load offset=20 + i32.store + local.get 2 + i32.const 0 + i32.store offset=44 + end + local.get 2 + i32.load offset=44 + local.set 1 + local.get 2 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat new file mode 100644 index 000000000..62093eb28 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -0,0 +1,1288 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $pred1 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $list_filter + drop + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + local.get 0 + i32.load offset=8 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=4 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 4 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 4 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + free + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_filter (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $list_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 12 + i32.add + call $list_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + call $list_add + drop + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $pred1 $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat new file mode 100644 index 000000000..2559569a5 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -0,0 +1,1404 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $pred2 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.gt_s + i32.const 1 + i32.and) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 3 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $list_filter + drop + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=8 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 0 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_filter (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $list_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 12 + i32.add + call $list_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + call $list_add + drop + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $pred2 $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat new file mode 100644 index 000000000..9e74ccf59 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat @@ -0,0 +1,1189 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat new file mode 100644 index 000000000..262be54ee --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat @@ -0,0 +1,1035 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat new file mode 100644 index 000000000..a522ab917 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -0,0 +1,1004 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1036 + call $list_new + drop + i32.const 1040 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1036 + call $list_destroy + i32.const 0 + i32.load offset=1040 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=16 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=12 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $list_index_of + drop + i32.const 0 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $list_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=28 + local.set 1 + local.get 0 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_index_of (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + local.get 4 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 4 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 4 + i32.load offset=8 + i32.load + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=16 + call_indirect (type 0) + br_if 0 (;@4;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=4 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 8 + i32.store offset=28 + end + local.get 4 + i32.load offset=28 + local.set 3 + local.get 4 + i32.const 32 + i32.add + global.set 0 + local.get 3) + (func $zero_if_ptr_eq (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const -1 + i32.xor + i32.const 1 + i32.and) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $zero_if_ptr_eq $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat new file mode 100644 index 000000000..ff130b855 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -0,0 +1,1752 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $list_new + drop + i32.const 1052 + call $list_new + drop + i32.const 0 + i32.const 1042 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1052 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_tests + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=52 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=56 + i32.store + local.get 0 + i32.load offset=56 + i32.const 0 + i32.load offset=1068 + i32.ne + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + call $list_iter_init + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1068 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1060 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + call $list_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load offset=52 + call $list_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 5 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 3 + local.get 0 + i32.const 24 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=24 + i32.load + local.get 0 + i32.load offset=52 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 4 + local.get 0 + i32.const 20 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=20 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + call $list_iter_init + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=52 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=16 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + call $list_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + i32.load + i32.const 0 + i32.load offset=1068 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load offset=52 + call $list_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=52 + i32.load + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_iter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12) + (func $list_iter_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + call $link_after + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $link_after (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + end) + (func $list_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "x\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat new file mode 100644 index 000000000..87fd18db7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -0,0 +1,1755 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $list_new + drop + i32.const 1052 + call $list_new + drop + i32.const 0 + i32.const 1042 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1052 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 4 + call $malloc + i32.store offset=40 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=36 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=32 + i32.store + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=28 + i32.store + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1068 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1060 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1048 + call $list_diter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $list_diter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1068 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.load offset=40 + call $list_diter_add + drop + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.load offset=36 + call $list_diter_add + drop + end + br 0 (;@2;) + end + end + i32.const 6 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + call $list_get_first + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + call $list_get_last + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 2 + local.get 0 + call $list_get_at + drop + local.get 0 + i32.load offset=36 + i32.load + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 4 + local.get 0 + call $list_get_at + drop + local.get 0 + i32.load offset=40 + i32.load + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $link_behind (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + end) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_diter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12) + (func $list_diter_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load + i32.store offset=4 + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + call $link_behind + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_diter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "y\00x\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat new file mode 100644 index 000000000..0d055954e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -0,0 +1,1598 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1044 + call $list_diter_init + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1064 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1064 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + call $list_diter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 0 + i32.load offset=20 + i32.load + i32.const 0 + i32.load offset=1052 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@4;) + local.get 0 + i32.load offset=20 + i32.load + i32.const 0 + i32.load offset=1060 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + end + local.get 0 + i32.const 24 + i32.add + i32.const 0 + call $list_diter_remove + drop + local.get 0 + i32.load offset=20 + free + end + br 0 (;@2;) + end + end + i32.const 2 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 16 + i32.add + call $list_get_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=16 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_diter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12) + (func $list_diter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call $unlinkn + i32.store + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_diter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat new file mode 100644 index 000000000..baa8afb12 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -0,0 +1,1519 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1052 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1064 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 24 + i32.add + call $list_get_at + drop + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1044 + call $list_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $list_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1060 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 8 + i32.add + i32.const 0 + call $list_iter_remove + drop + end + br 0 (;@2;) + end + end + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=24 + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=24 + free + call $teardown_test + local.get 0 + i32.load offset=28 + local.set 1 + local.get 0 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_iter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12) + (func $list_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call $unlinkn + i32.store + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat new file mode 100644 index 000000000..8e02caa25 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -0,0 +1,1254 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (func $pred1 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + call $list_filter_mut + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $list_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 2) + br_if 0 (;@4;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $pred1 $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat new file mode 100644 index 000000000..365fc0f29 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -0,0 +1,1374 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $pred2 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.gt_s + i32.const 1 + i32.and) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.const 3 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 3 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + call $list_filter_mut + drop + i32.const 1 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $list_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 2) + br_if 0 (;@4;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $pred2 $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat new file mode 100644 index 000000000..633f25c49 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat @@ -0,0 +1,750 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1028 + call $list_new + drop + i32.const 1032 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1028 + call $list_destroy + i32.const 0 + i32.load offset=1032 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1028 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1032 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 0 + i32.load offset=1028 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=12 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1028 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + local.get 0 + i32.load offset=12 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1028 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1028 + i32.const 0 + i32.load offset=1032 + i32.ne + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1024 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1024 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1024 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1024 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1024 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1024 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1024 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1024 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat new file mode 100644 index 000000000..496d75c5b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -0,0 +1,1451 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1052 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1064 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + i32.const 0 + call $list_remove + drop + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + free + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_remove (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_node + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.load + i32.store + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $unlinkn + drop + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load + i32.load + local.get 2 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 3 (;@1;) + end + local.get 2 + local.get 2 + i32.load + i32.load offset=4 + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat new file mode 100644 index 000000000..e5c09b203 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat @@ -0,0 +1,1076 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_remove_all_cb + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=12 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat new file mode 100644 index 000000000..ad97b230c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat @@ -0,0 +1,1319 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $list_remove_at + drop + local.get 0 + i32.load offset=12 + free + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $list_remove_at + drop + local.get 0 + i32.load offset=12 + free + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 12 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_remove_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.load + i32.store + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $unlinkn + drop + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat new file mode 100644 index 000000000..4433c8ba0 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat @@ -0,0 +1,1123 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_remove_first + drop + local.get 0 + i32.load offset=12 + free + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $unlinkn + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat new file mode 100644 index 000000000..e407ac4cf --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat @@ -0,0 +1,1127 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_remove_last + drop + local.get 0 + i32.load offset=12 + free + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1060 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call $unlinkn + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat new file mode 100644 index 000000000..f213d98f9 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat @@ -0,0 +1,1282 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $list_new + drop + i32.const 1052 + call $list_new + drop + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1052 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_replace_at + drop + local.get 0 + i32.load offset=4 + free + i32.const 0 + i32.load offset=1048 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_replace_at (type 7) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=28 + local.get 4 + local.get 1 + i32.store offset=24 + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + local.get 3 + i32.store offset=16 + local.get 4 + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=20 + local.get 4 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=8 + block ;; label = @1 + local.get 4 + i32.load offset=8 + br_if 0 (;@1;) + local.get 4 + local.get 4 + i32.load offset=12 + i32.load + i32.store offset=4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + i32.store + block ;; label = @2 + local.get 4 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=4 + i32.store + end + end + local.get 4 + i32.load offset=8 + local.set 3 + local.get 4 + i32.const 32 + i32.add + global.set 0 + local.get 3) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "r\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat new file mode 100644 index 000000000..243069403 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat @@ -0,0 +1,1711 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1044 + call $list_reverse + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $list_get_first + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_reverse (type 1) (param i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=28 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=28 + i32.load + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=28 + i32.load offset=4 + i32.store offset=24 + local.get 1 + local.get 1 + i32.load offset=28 + i32.load offset=8 + i32.store offset=20 + local.get 1 + local.get 1 + i32.load offset=28 + i32.load offset=4 + i32.store offset=16 + local.get 1 + local.get 1 + i32.load offset=28 + i32.load offset=8 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=28 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 1 + local.get 1 + i32.load offset=16 + i32.load offset=4 + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=12 + i32.load offset=8 + i32.store + local.get 1 + i32.load offset=16 + local.get 1 + i32.load offset=12 + call $swap + local.get 1 + local.get 1 + i32.load offset=4 + i32.store offset=16 + local.get 1 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 1 + i32.load offset=28 + local.get 1 + i32.load offset=20 + i32.store offset=4 + local.get 1 + i32.load offset=28 + local.get 1 + i32.load offset=24 + i32.store offset=8 + end + local.get 1 + i32.const 32 + i32.add + global.set 0) + (func $swap (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=28 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + call $swap_adjacent + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=8 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=24 + i32.store offset=4 + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=20 + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.store offset=8 + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=4 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=28 + i32.store offset=4 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=12 + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=28 + i32.store offset=8 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=8 + i32.store offset=4 + end + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $swap_adjacent (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=12 + i32.store offset=8 + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=12 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.store offset=4 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=4 + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + end) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat new file mode 100644 index 000000000..d46ada36f --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat @@ -0,0 +1,1362 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32))) + (type (;6;) (func (param i32 i32))) + (func $setup_tests (type 2) + i32.const 1036 + call $list_new + drop + i32.const 1040 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1036 + call $list_destroy + i32.const 0 + i32.load offset=1040 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=28 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 40 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 28 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1036 + i32.const 1 + call $list_sort + drop + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1036 + call $list_iter_init + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $list_iter_next + drop + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + call $list_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load + i32.load + i32.le_s + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load + i32.store offset=4 + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $qsort (type 5) (param i32 i32 i32 i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 3 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=16 + local.get 4 + local.get 4 + i32.load offset=16 + i32.store offset=12 + local.get 4 + i32.const 0 + i32.store offset=28 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=40 + i32.const 1 + i32.sub + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + local.get 4 + i32.load offset=28 + i32.store offset=20 + local.get 4 + local.get 4 + i32.load offset=28 + i32.const 1 + i32.add + i32.store offset=24 + block ;; label = @3 + loop ;; label = @4 + local.get 4 + i32.load offset=24 + local.get 4 + i32.load offset=40 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + block ;; label = @5 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=24 + local.get 4 + i32.load offset=36 + i32.mul + i32.add + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=36 + i32.mul + i32.add + local.get 4 + i32.load offset=32 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 4 + local.get 4 + i32.load offset=24 + i32.store offset=20 + end + local.get 4 + local.get 4 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + br 0 (;@4;) + end + end + local.get 4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=36 + i32.mul + i32.add + i32.store offset=8 + local.get 4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=36 + i32.mul + i32.add + i32.store offset=4 + local.get 4 + local.get 4 + i32.load offset=8 + i32.load + i32.store + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=4 + i32.load + i32.store + local.get 4 + i32.load offset=4 + local.get 4 + i32.load + i32.store + local.get 4 + local.get 4 + i32.load offset=28 + i32.const 1 + i32.add + i32.store offset=28 + br 0 (;@2;) + end + end + local.get 4 + i32.const 48 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_to_array (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 3 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 4 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=12 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_sort (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 16 + i32.add + call $list_to_array + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.const 4 + local.get 2 + i32.load offset=20 + call $qsort + local.get 2 + i32.const 0 + i32.store offset=4 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_iter_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12) + (func $list_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat new file mode 100644 index 000000000..77a31a8d3 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat @@ -0,0 +1,1627 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $list_splice + drop + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1080 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 4 + local.get 0 + i32.const 12 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_splice (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + call $list_splice_at + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_splice_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load + i32.store + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store offset=4 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 12 + i32.add + call $get_node_at + drop + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.sub + local.get 3 + i32.const 8 + i32.add + call $get_node_at + drop + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + call $splice_between + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $splice_between (type 7) (param i32 i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=12 + local.get 4 + local.get 1 + i32.store offset=8 + local.get 4 + local.get 2 + i32.store offset=4 + local.get 4 + local.get 3 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + i32.load offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=12 + i32.load offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + local.get 4 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 4 + i32.load offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + local.get 4 + i32.load offset=4 + i32.store offset=8 + local.get 4 + i32.load + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load + i32.store offset=4 + end + end + local.get 4 + i32.load offset=12 + local.tee 3 + local.get 3 + i32.load + local.get 4 + i32.load offset=8 + i32.load + i32.add + i32.store + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat new file mode 100644 index 000000000..c5134ed84 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat @@ -0,0 +1,1601 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32 i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + i32.const 2 + call $list_splice_at + drop + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $list_get_last + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_splice_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load offset=8 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.load + i32.store + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store offset=4 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 12 + i32.add + call $get_node_at + drop + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.sub + local.get 3 + i32.const 8 + i32.add + call $get_node_at + drop + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + call $splice_between + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $splice_between (type 7) (param i32 i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=12 + local.get 4 + local.get 1 + i32.store offset=8 + local.get 4 + local.get 2 + i32.store offset=4 + local.get 4 + local.get 3 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + i32.load offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=12 + i32.load offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + local.get 4 + i32.load offset=12 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 4 + i32.load offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + local.get 4 + i32.load offset=4 + i32.store offset=8 + local.get 4 + i32.load + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load + i32.store offset=4 + end + end + local.get 4 + i32.load offset=12 + local.tee 3 + local.get 3 + i32.load + local.get 4 + i32.load offset=8 + i32.load + i32.add + i32.store + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat new file mode 100644 index 000000000..f061b522e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat @@ -0,0 +1,1406 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + call $setup_tests + i32.const 0 + i32.load offset=1044 + i32.const 1 + i32.const 2 + local.get 0 + i32.const 12 + i32.add + call $list_sublist + drop + i32.const 2 + local.get 0 + i32.load offset=12 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $list_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + call $list_destroy + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_sublist (type 7) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=40 + local.get 4 + local.get 1 + i32.store offset=36 + local.get 4 + local.get 2 + i32.store offset=32 + local.get 4 + local.get 3 + i32.store offset=28 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load offset=36 + local.get 4 + i32.load offset=32 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 4 + i32.const 3 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=40 + i32.load offset=12 + i32.store offset=16 + local.get 4 + local.get 4 + i32.load offset=40 + i32.load offset=16 + i32.store offset=20 + local.get 4 + local.get 4 + i32.load offset=40 + i32.load offset=20 + i32.store offset=24 + local.get 4 + local.get 4 + i32.const 16 + i32.add + local.get 4 + i32.const 12 + i32.add + call $list_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 4 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 4 + local.get 4 + i32.load offset=8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=40 + local.get 4 + i32.load offset=36 + local.get 4 + i32.const 4 + i32.add + call $get_node_at + i32.store offset=8 + block ;; label = @2 + local.get 4 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=40 + i32.load offset=20 + call_indirect (type 1) + local.get 4 + local.get 4 + i32.load offset=8 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=36 + i32.store + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load + local.get 4 + i32.load offset=32 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=4 + i32.load + call $list_add + i32.store offset=8 + block ;; label = @4 + local.get 4 + i32.load offset=8 + i32.eqz + br_if 0 (;@4;) + local.get 4 + i32.load offset=12 + call $list_destroy + local.get 4 + local.get 4 + i32.load offset=8 + i32.store offset=44 + br 3 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + local.get 4 + local.get 4 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=12 + i32.store + local.get 4 + i32.const 0 + i32.store offset=44 + end + local.get 4 + i32.load offset=44 + local.set 3 + local.get 4 + i32.const 48 + i32.add + global.set 0 + local.get 3) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat new file mode 100644 index 000000000..d1221d369 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat @@ -0,0 +1,1342 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $list_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $list_destroy_cb + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_tests + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $list_to_array + drop + local.get 0 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load + i32.const 4 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + local.get 0 + i32.const 4 + i32.add + call $list_get_at + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + local.get 0 + i32.load offset=8 + free + call $teardown_test + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.shr_u + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @4 + loop ;; label = @5 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@4;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@5;) + end + end + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.store offset=12 + block ;; label = @3 + loop ;; label = @4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@3;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const -1 + i32.add + i32.store offset=12 + br 0 (;@4;) + end + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=24 + local.get 3 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @1 + local.get 3 + i32.load offset=12 + br_if 0 (;@1;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=16 + i32.load + i32.store + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $list_to_array (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 3 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 4 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=12 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat new file mode 100644 index 000000000..f575f3877 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -0,0 +1,2331 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (type (;7;) (func (param i32 i32 i32))) + (type (;8;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1052 + call $list_new + drop + i32.const 1056 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1052 + call $list_destroy + i32.const 0 + i32.load offset=1056 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 144 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=140 + call $setup_tests + local.get 0 + i32.const 1044 + i32.symbolic + i32.store offset=136 + local.get 0 + i32.load offset=136 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=136 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=136 + i32.store8 offset=134 + local.get 0 + i32.const 0 + i32.store8 offset=135 + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=128 + local.get 0 + i32.load offset=128 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=128 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=128 + i32.store8 offset=126 + local.get 0 + i32.const 0 + i32.store8 offset=127 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=136 + local.get 0 + i32.load offset=128 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=136 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=136 + local.get 0 + i32.load offset=112 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=136 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=136 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=112 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=112 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=56 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 134 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 126 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 118 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 110 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 102 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 94 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 86 + i32.add + call $list_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + call $list_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $list_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 126 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.const 70 + i32.add + call $list_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $list_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 70 + i32.add + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $list_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 118 + i32.add + i32.const 1 + local.get 0 + i32.const 12 + i32.add + call $list_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 70 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 5 + i32.const 0 + i32.load offset=1052 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 4 + i32.const 0 + i32.load offset=1056 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + call $list_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $list_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=16 + local.get 0 + i32.const 86 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 54 + i32.add + call $list_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.const 110 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 8 + i32.add + call $list_get_last + drop + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + call $teardown_test + local.get 0 + i32.load offset=140 + local.set 1 + local.get 0 + i32.const 144 + i32.add + global.set 0 + local.get 1) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1048 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1048 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1048 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1048 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $list_index_of (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + local.get 4 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 4 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 4 + i32.load offset=8 + i32.load + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=16 + call_indirect (type 0) + br_if 0 (;@4;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=4 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 8 + i32.store offset=28 + end + local.get 4 + i32.load offset=28 + local.set 3 + local.get 4 + i32.const 32 + i32.add + global.set 0 + local.get 3) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $link_after (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + end) + (func $list_zip_iter_init (type 7) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=20) + (func $list_zip_iter_next (type 8) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_zip_iter_add (type 8) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 1 + i32.const 12 + local.get 3 + i32.load offset=24 + i32.load + i32.load offset=16 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 1 + i32.const 12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=12 + call $link_after + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=8 + call $link_after + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=8 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.store offset=8 + end + local.get 3 + i32.load offset=24 + i32.load + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $CHECK_EQUAL_C_STRING (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $zero_if_ptr_eq (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const -1 + i32.xor + i32.const 1 + i32.and) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66608)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $zero_if_ptr_eq $malloc $calloc $free) + (data (;0;) (i32.const 1024) "y\00x\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1048) "0\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat new file mode 100644 index 000000000..c5d036928 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat @@ -0,0 +1,1231 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_tests (type 2) + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $list_destroy + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 112 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=108 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 102 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 70 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $list_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $list_zip_iter_init + local.get 0 + i32.const 0 + i32.store offset=20 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $list_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=20 + br_if 0 (;@3;) + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.load offset=16 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.load offset=12 + call $CHECK_EQUAL_C_STRING + end + block ;; label = @3 + local.get 0 + i32.load offset=20 + i32.const 2 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.load offset=16 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=12 + call $CHECK_EQUAL_C_STRING + end + local.get 0 + local.get 0 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + br 0 (;@2;) + end + end + i32.const 3 + local.get 0 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=108 + local.set 1 + local.get 0 + i32.const 112 + i32.add + global.set 0 + local.get 1) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_zip_iter_init (type 5) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=20) + (func $list_zip_iter_next (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $CHECK_EQUAL_C_STRING (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat new file mode 100644 index 000000000..35906e256 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -0,0 +1,1760 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_tests (type 2) + i32.const 1044 + call $list_new + drop + i32.const 1048 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $list_destroy + i32.const 0 + i32.load offset=1048 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 112 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=108 + call $setup_tests + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=64 + local.get 0 + i32.load offset=56 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 102 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 70 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $list_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $list_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $list_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 94 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $list_zip_iter_remove + drop + end + br 0 (;@2;) + end + end + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.load offset=12 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + i32.const 0 + i32.load offset=1048 + call $list_size + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=108 + local.set 1 + local.get 0 + i32.const 112 + i32.add + global.set 0 + local.get 1) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $list_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $list_zip_iter_init (type 5) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=20) + (func $list_zip_iter_next (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_zip_iter_remove (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=8 + call $unlinkn + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=24 + i32.load offset=12 + call $unlinkn + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $CHECK_EQUAL_C_STRING (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat new file mode 100644 index 000000000..664d6213e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -0,0 +1,1841 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32 i32) (result i32))) + (type (;8;) (func (param i32 i32 i32 i32 i32) (result i32))) + (func $setup_tests (type 2) + i32.const 1048 + call $list_new + drop + i32.const 1052 + call $list_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $list_destroy + i32.const 0 + i32.load offset=1052 + call $list_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 128 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=124 + call $setup_tests + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=112 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=112 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=64 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=64 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=80 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=72 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=56 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=56 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 118 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 110 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 102 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 94 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 86 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + call $list_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 70 + i32.add + call $list_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1052 + call $list_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $list_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=20 + local.get 0 + i32.const 110 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $list_zip_iter_replace + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $list_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 54 + i32.add + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $list_index_of + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 54 + i32.add + call $list_contains + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.load offset=124 + local.set 1 + local.get 0 + i32.const 128 + i32.add + global.set 0 + local.get 1) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $list_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $list_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $list_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $list_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 1 + i32.load offset=12 + call $list_remove_all + drop + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $list_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $unlinkn + drop + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $list_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $list_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + block ;; label = @1 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.load offset=12 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $list_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $list_index_of (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + local.get 4 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 4 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 4 + i32.load offset=8 + i32.load + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=16 + call_indirect (type 0) + br_if 0 (;@4;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=4 + i32.store + local.get 4 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 8 + i32.store offset=28 + end + local.get 4 + i32.load offset=28 + local.set 3 + local.get 4 + i32.const 32 + i32.add + global.set 0 + local.get 3) + (func $list_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=20) + (func $list_zip_iter_next (type 7) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=8 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $list_zip_iter_replace (type 8) (param i32 i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 5 + local.get 0 + i32.store offset=24 + local.get 5 + local.get 1 + i32.store offset=20 + local.get 5 + local.get 2 + i32.store offset=16 + local.get 5 + local.get 3 + i32.store offset=12 + local.get 5 + local.get 4 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 5 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 5 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 5 + local.get 5 + i32.load offset=24 + i32.load offset=8 + i32.load + i32.store offset=4 + local.get 5 + local.get 5 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store + local.get 5 + i32.load offset=24 + i32.load offset=8 + local.get 5 + i32.load offset=20 + i32.store + local.get 5 + i32.load offset=24 + i32.load offset=12 + local.get 5 + i32.load offset=16 + i32.store + block ;; label = @2 + local.get 5 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 5 + i32.load offset=12 + local.get 5 + i32.load offset=4 + i32.store + end + block ;; label = @2 + local.get 5 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 5 + i32.load offset=8 + local.get 5 + i32.load + i32.store + end + local.get 5 + i32.const 0 + i32.store offset=28 + end + local.get 5 + i32.load offset=28) + (func $zero_if_ptr_eq (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const -1 + i32.xor + i32.const 1 + i32.and) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $zero_if_ptr_eq $malloc $calloc $free) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat new file mode 100644 index 000000000..ab67965ad --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -0,0 +1,1434 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + i32.const 1040 + i32.const 1 + call $pqueue_new + drop + local.get 0 + i32.const 8 + i32.add + i32.const 2 + call $pqueue_conf_init + local.get 0 + i32.const 8 + i32.add + i32.const 1044 + call $pqueue_new_conf + drop + local.get 0 + i32.const 32 + i32.add + global.set 0) + (func $comp2 (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.sub) + (func $comp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.sub + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.sub + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1040 + call $pqueue_destroy + i32.const 0 + i32.load offset=1044 + call $pqueue_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=24 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=24 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=20 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=20 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $pqueue_push + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $pqueue_top + drop + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $pqueue_push + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $pqueue_top + drop + block ;; label = @1 + block ;; label = @2 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + i32.const 1 + local.set 1 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=16 + i32.load + i32.eq + i32.const 1 + i32.and + br_if 1 (;@1;) + end + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=20 + i32.le_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=16 + i32.load + i32.eq + local.set 1 + end + end + local.get 1 + i32.const 1 + i32.and + sym_assert + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=40 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=40 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=36 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=36 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=32 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=32 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=28 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=28 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.get 0 + i32.load offset=40 + i32.store offset=1048 + i32.const 0 + local.get 0 + i32.load offset=36 + i32.store offset=1052 + i32.const 0 + local.get 0 + i32.load offset=32 + i32.store offset=1056 + i32.const 0 + local.get 0 + i32.load offset=28 + i32.store offset=1060 + i32.const 0 + i32.load offset=1044 + i32.const 1048 + call $pqueue_push + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $pqueue_top + drop + i32.const 1048 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1056 + call $pqueue_push + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 12 + i32.add + call $pqueue_top + drop + block ;; label = @1 + block ;; label = @2 + i32.const 1048 + i32.const 1056 + call $comp + i32.const 0 + i32.ge_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + i32.const 1 + local.set 1 + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + br_if 1 (;@1;) + end + i32.const 0 + local.set 1 + block ;; label = @2 + i32.const 1048 + i32.const 1056 + call $comp + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.load offset=28 + local.get 0 + i32.load offset=12 + i32.load offset=4 + i32.eq + local.set 1 + end + end + end + local.get 1 + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $pqueue_conf_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 3 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 4 + i32.store offset=16 + local.get 2 + i32.load offset=12 + i32.const 5 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 8 + i32.store) + (func $pqueue_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + call $pqueue_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + call $pqueue_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $pqueue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=24 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=28 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $pqueue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $pqueue_push (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + call $expand_capacity + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=20 + i32.store + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=16 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load offset=28 + call_indirect (type 0) + i32.const 0 + i32.gt_s + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + br 1 (;@2;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $pqueue_top (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 6 6 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66608)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $comp2 $comp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) "0\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat new file mode 100644 index 000000000..2c4969655 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -0,0 +1,1657 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $setup_tests (type 3) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + i32.const 1 + call $pqueue_new + drop + local.get 0 + i32.const 8 + i32.add + i32.const 2 + call $pqueue_conf_init + local.get 0 + i32.const 8 + i32.add + i32.const 1052 + call $pqueue_new_conf + drop + local.get 0 + i32.const 32 + i32.add + global.set 0) + (func $comp2 (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.sub) + (func $comp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.sub + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.sub + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1048 + call $pqueue_destroy + i32.const 0 + i32.load offset=1052 + call $pqueue_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_tests + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=16 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=16 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=12 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=12 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=8 + i32.const 8388608 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=8 + i32.const -8388608 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=8 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=12 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $pqueue_push + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 16 + i32.add + call $pqueue_push + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 8 + i32.add + call $pqueue_push + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 4 + i32.add + call $pqueue_pop + drop + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 4 + i32.add + call $pqueue_pop + drop + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 4 + i32.add + call $pqueue_pop + drop + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + local.get 0 + i32.load offset=40 + i32.store offset=1056 + i32.const 0 + local.get 0 + i32.load offset=36 + i32.store offset=1060 + i32.const 0 + local.get 0 + i32.load offset=32 + i32.store offset=1064 + i32.const 0 + local.get 0 + i32.load offset=28 + i32.store offset=1068 + i32.const 0 + local.get 0 + i32.load offset=24 + i32.store offset=1072 + i32.const 0 + local.get 0 + i32.load offset=20 + i32.store offset=1076 + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 1072 + i32.const 1056 + call $comp + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 1056 + i32.const 1064 + call $comp + i32.const 0 + i32.gt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1052 + i32.const 1056 + call $pqueue_push + drop + i32.const 0 + i32.load offset=1052 + i32.const 1064 + call $pqueue_push + drop + i32.const 0 + i32.load offset=1052 + i32.const 1072 + call $pqueue_push + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + call $pqueue_pop + drop + i32.const 1072 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + call $pqueue_pop + drop + i32.const 1056 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + call $pqueue_pop + drop + i32.const 1064 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $pqueue_conf_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 3 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 4 + i32.store offset=16 + local.get 2 + i32.load offset=12 + i32.const 5 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 8 + i32.store) + (func $pqueue_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + call $pqueue_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + call $pqueue_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $pqueue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=24 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=28 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $pqueue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $pqueue_push (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + call $expand_capacity + i32.store offset=12 + block ;; label = @3 + local.get 2 + i32.load offset=12 + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=20 + i32.store + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=16 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load offset=28 + call_indirect (type 0) + i32.const 0 + i32.gt_s + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.const 1 + i32.sub + i32.const 1 + i32.shr_u + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=4 + br 1 (;@2;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $pqueue_pop (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load + i32.store + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 1 + i32.sub + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.load offset=8 + i32.const 0 + call $pqueue_heapify + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $pqueue_heapify (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=44 + local.get 2 + local.get 1 + i32.store offset=40 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=44 + i32.load + i32.const 1 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=40 + i32.const 1 + i32.shl + i32.const 1 + i32.add + i32.store offset=36 + local.get 2 + local.get 2 + i32.load offset=40 + i32.const 1 + i32.shl + i32.const 2 + i32.add + i32.store offset=32 + local.get 2 + local.get 2 + i32.load offset=40 + i32.store offset=28 + local.get 2 + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=36 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=32 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=40 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=16 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=36 + local.get 2 + i32.load offset=44 + i32.load + i32.ge_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=32 + local.get 2 + i32.load offset=44 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=44 + i32.load offset=28 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=36 + i32.store offset=40 + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=44 + i32.load offset=28 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=20 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=32 + i32.store offset=40 + end + local.get 2 + i32.load offset=40 + local.get 2 + i32.load offset=28 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=28 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=40 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=44 + i32.load offset=12 + local.get 2 + i32.load offset=40 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=44 + local.get 2 + i32.load offset=40 + call $pqueue_heapify + end + local.get 2 + i32.const 48 + i32.add + global.set 0) + (func $assume (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 6 6 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $comp2 $comp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat new file mode 100644 index 000000000..69e0cb19a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat @@ -0,0 +1,1319 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_test (type 3) + i32.const 1036 + call $queue_new + drop + i32.const 1040 + call $queue_new + drop) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1036 + call $queue_destroy + i32.const 0 + i32.load offset=1040 + call $queue_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $queue_enqueue + drop + i32.const 2 + i32.const 0 + i32.load offset=1036 + call $queue_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_peek + drop + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_peek + drop + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $deque_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $queue_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $deque_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $queue_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $queue_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $queue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $deque_new_conf + drop + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=12 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $queue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $deque_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_get_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_enqueue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_add_first + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_size (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $deque_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat new file mode 100644 index 000000000..f58d4e257 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat @@ -0,0 +1,1460 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_test (type 3) + i32.const 1036 + call $queue_new + drop + i32.const 1040 + call $queue_new + drop) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1036 + call $queue_destroy + i32.const 0 + i32.load offset=1040 + call $queue_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_test + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 40 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $queue_enqueue + drop + local.get 0 + i32.const 0 + i32.store offset=28 + local.get 0 + i32.const 0 + i32.store offset=24 + local.get 0 + i32.const 0 + i32.store offset=20 + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1036 + call $queue_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $queue_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 40 + i32.add + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=28 + i32.const 1 + i32.add + i32.store offset=28 + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 36 + i32.add + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=24 + i32.const 1 + i32.add + i32.store offset=24 + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + local.get 0 + i32.const 32 + i32.add + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=20 + i32.const 1 + i32.add + i32.store offset=20 + end + br 0 (;@2;) + end + end + i32.const 1 + local.get 0 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=8) + (func $deque_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=12 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + i32.load offset=4 + local.get 2 + i32.load offset=24 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.add + local.get 2 + i32.load offset=16 + i32.and + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + local.get 2 + i32.load offset=24 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=24 + i32.load + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $queue_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $deque_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $queue_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $queue_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $queue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $deque_new_conf + drop + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=12 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $queue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $deque_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_enqueue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_add_first + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + call $deque_iter_init + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $queue_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $deque_iter_next + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat new file mode 100644 index 000000000..92b731f61 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat @@ -0,0 +1,1417 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_test (type 3) + i32.const 1036 + call $queue_new + drop + i32.const 1040 + call $queue_new + drop) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1036 + call $queue_destroy + i32.const 0 + i32.load offset=1040 + call $queue_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_poll + drop + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_peek + drop + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_poll + drop + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $queue_peek + drop + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $deque_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $queue_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $deque_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $queue_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $queue_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $queue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $deque_new_conf + drop + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=12 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $queue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $deque_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_get_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_poll (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_remove_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_enqueue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_add_first + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat new file mode 100644 index 000000000..7d08a848a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat @@ -0,0 +1,1745 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_test (type 3) + i32.const 1044 + call $queue_new + drop + i32.const 1048 + call $queue_new + drop) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $queue_destroy + i32.const 0 + i32.load offset=1048 + call $queue_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + call $setup_test + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=88 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=80 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 70 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 62 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 46 + i32.add + call $queue_enqueue + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 38 + i32.add + call $queue_enqueue + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $queue_zip_iter_init + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $queue_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + br_if 0 (;@3;) + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 38 + i32.add + local.get 0 + i32.load offset=4 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.const 2 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=4 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + end + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $deque_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $deque_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 1) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load offset=8 + i32.load + call $upper_pow_two + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $upper_pow_two (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.const -2147483648 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const -2147483648 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 1 + i32.load offset=8 + br_if 0 (;@2;) + local.get 1 + i32.const 2 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 2 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 4 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 8 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.const 16 + i32.shr_u + i32.or + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.store offset=12 + end + local.get 1 + i32.load offset=12) + (func $deque_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const -2147483648 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.shl + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 4 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 0) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.const 0 + call $copy_buffer + local.get 1 + i32.load offset=8 + i32.load offset=16 + local.get 1 + i32.load offset=8 + i32.load offset=28 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=16 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $deque_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $copy_buffer (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=28 + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.gt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + br 1 (;@3;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=12 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.sub + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=28 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + call $memcpy + drop + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=16 + i32.const 2 + i32.shl + call $memcpy + drop + end + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.const 1 + i32.sub + i32.and + i32.store offset=4 + local.get 3 + i32.load offset=28 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 1) + local.set 2 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.store + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.const 32 + i32.add + global.set 0) + (func $deque_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=12) + (func $deque_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=28 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=12 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=4 + i32.const 1 + i32.sub + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=12 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.and + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=40 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=28 + i32.and + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=8 + local.get 3 + i32.load offset=40 + i32.load offset=8 + i32.add + local.get 3 + i32.load offset=16 + i32.and + i32.store + local.get 3 + i32.load offset=36 + local.get 3 + i32.load offset=40 + i32.load + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=32 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.load offset=16 + local.get 3 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + i32.load offset=40 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44) + (func $queue_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $deque_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $queue_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $queue_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $queue_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $deque_new_conf + drop + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=12 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $queue_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $deque_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $queue_enqueue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $deque_add_first + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $queue_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=4 + i32.load + call $deque_zip_iter_init + local.get 3 + i32.const 16 + i32.add + global.set 0) + (func $queue_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=4 + call $deque_zip_iter_next + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat new file mode 100644 index 000000000..d268fa45a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat @@ -0,0 +1,927 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1052 + call $rbuf_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1052 + call $rbuf_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 160 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=156 + call $setup_test + local.get 0 + i32.const 1046 + i32.symbolic + i32.store offset=108 + local.get 0 + local.get 0 + i32.load offset=108 + i32.store8 offset=106 + local.get 0 + i32.const 0 + i32.store8 offset=107 + local.get 0 + i32.const 1044 + i32.symbolic + i32.store offset=100 + local.get 0 + local.get 0 + i32.load offset=100 + i32.store8 offset=98 + local.get 0 + i32.const 0 + i32.store8 offset=99 + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=92 + local.get 0 + local.get 0 + i32.load offset=92 + i32.store8 offset=90 + local.get 0 + i32.const 0 + i32.store8 offset=91 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=84 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store8 offset=82 + local.get 0 + i32.const 0 + i32.store8 offset=83 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=76 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store8 offset=74 + local.get 0 + i32.const 0 + i32.store8 offset=75 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=68 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store8 offset=66 + local.get 0 + i32.const 0 + i32.store8 offset=67 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=60 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store8 offset=58 + local.get 0 + i32.const 0 + i32.store8 offset=59 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store8 offset=50 + local.get 0 + i32.const 0 + i32.store8 offset=51 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store8 offset=34 + local.get 0 + i32.const 0 + i32.store8 offset=35 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=108 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=100 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=92 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=84 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=76 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=68 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=60 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=52 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=44 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=36 + call $rbuf_enqueue + local.get 0 + i32.const 112 + i32.add + local.tee 1 + i64.const 0 + i64.store + local.get 1 + i32.const 32 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 24 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 16 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 8 + i32.add + i64.const 0 + i64.store + local.get 0 + local.get 0 + i32.load offset=108 + i32.store offset=112 + local.get 0 + local.get 0 + i32.load offset=100 + i32.store offset=116 + local.get 0 + local.get 0 + i32.load offset=92 + i32.store offset=120 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store offset=124 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store offset=128 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store offset=132 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store offset=136 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store offset=140 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store offset=144 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store offset=148 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.load offset=1052 + i32.const 0 + call $rbuf_peek + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=116 + i32.const 0 + i32.load offset=1052 + i32.const 1 + call $rbuf_peek + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 26 + i32.add + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 18 + i32.add + call $rbuf_enqueue + i32.const 0 + i32.load offset=1052 + i32.const 0 + call $rbuf_peek + local.get 0 + i32.const 26 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + i32.const 1 + call $rbuf_peek + local.get 0 + i32.const 18 + i32.add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 12 + i32.add + call $rbuf_dequeue + drop + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 160 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1048 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1048 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1048 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1048 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $rbuf_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $rbuf_conf_new + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $rbuf_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 10 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $rbuf_conf_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $rbuf_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_is_empty (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $rbuf_enqueue (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end) + (func $rbuf_dequeue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + call $rbuf_is_empty + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.rem_u + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $rbuf_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "y\00x\00j\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1048) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat new file mode 100644 index 000000000..9546a08f5 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat @@ -0,0 +1,865 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1048 + call $rbuf_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $rbuf_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 144 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=140 + call $setup_test + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=92 + local.get 0 + local.get 0 + i32.load offset=92 + i32.store8 offset=90 + local.get 0 + i32.const 0 + i32.store8 offset=91 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=84 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store8 offset=82 + local.get 0 + i32.const 0 + i32.store8 offset=83 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=76 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store8 offset=74 + local.get 0 + i32.const 0 + i32.store8 offset=75 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=68 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store8 offset=66 + local.get 0 + i32.const 0 + i32.store8 offset=67 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=60 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store8 offset=58 + local.get 0 + i32.const 0 + i32.store8 offset=59 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store8 offset=50 + local.get 0 + i32.const 0 + i32.store8 offset=51 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store8 offset=34 + local.get 0 + i32.const 0 + i32.store8 offset=35 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=92 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=84 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=76 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=68 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=60 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=52 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=44 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=36 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=28 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=20 + call $rbuf_enqueue + local.get 0 + i32.const 96 + i32.add + local.tee 1 + i64.const 0 + i64.store + local.get 1 + i32.const 32 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 24 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 16 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 8 + i32.add + i64.const 0 + i64.store + local.get 0 + local.get 0 + i32.load offset=92 + i32.store offset=96 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store offset=100 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store offset=104 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store offset=108 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store offset=112 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store offset=116 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store offset=120 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store offset=124 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store offset=128 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store offset=132 + local.get 0 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load offset=8 + i32.const 10 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $rbuf_dequeue + drop + local.get 0 + i32.const 96 + i32.add + local.get 0 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 12 + i32.add + i32.const 0 + i32.store + local.get 0 + local.get 0 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.const 144 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $rbuf_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $rbuf_conf_new + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $rbuf_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 10 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $rbuf_conf_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $rbuf_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_is_empty (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $rbuf_enqueue (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end) + (func $rbuf_dequeue (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + call $rbuf_is_empty + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.rem_u + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "j\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat new file mode 100644 index 000000000..a7cd653e4 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat @@ -0,0 +1,791 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1048 + call $rbuf_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $rbuf_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 144 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=140 + call $setup_test + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=92 + local.get 0 + local.get 0 + i32.load offset=92 + i32.store8 offset=90 + local.get 0 + i32.const 0 + i32.store8 offset=91 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=84 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store8 offset=82 + local.get 0 + i32.const 0 + i32.store8 offset=83 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=76 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store8 offset=74 + local.get 0 + i32.const 0 + i32.store8 offset=75 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=68 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store8 offset=66 + local.get 0 + i32.const 0 + i32.store8 offset=67 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=60 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store8 offset=58 + local.get 0 + i32.const 0 + i32.store8 offset=59 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store8 offset=50 + local.get 0 + i32.const 0 + i32.store8 offset=51 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store8 offset=34 + local.get 0 + i32.const 0 + i32.store8 offset=35 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=92 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=84 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=76 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=68 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=60 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=52 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=44 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=36 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=28 + call $rbuf_enqueue + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=20 + call $rbuf_enqueue + local.get 0 + i32.const 96 + i32.add + local.tee 1 + i64.const 0 + i64.store + local.get 1 + i32.const 32 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 24 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 16 + i32.add + i64.const 0 + i64.store + local.get 1 + i32.const 8 + i32.add + i64.const 0 + i64.store + local.get 0 + local.get 0 + i32.load offset=92 + i32.store offset=96 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store offset=100 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store offset=104 + local.get 0 + local.get 0 + i32.load offset=68 + i32.store offset=108 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store offset=112 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store offset=116 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store offset=120 + local.get 0 + local.get 0 + i32.load offset=36 + i32.store offset=124 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store offset=128 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store offset=132 + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.load offset=12 + i32.const 10 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $rbuf_peek + local.get 0 + i32.const 96 + i32.add + local.get 0 + i32.load offset=12 + i32.const 2 + i32.shl + i32.add + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.const 144 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $rbuf_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $rbuf_conf_new + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $rbuf_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 10 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=12) + (func $rbuf_conf_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 32 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=8 + i32.load + i32.const 4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + call_indirect (type 0) + local.set 1 + local.get 2 + i32.load + local.get 1 + i32.store offset=16 + block ;; label = @2 + local.get 1 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=20 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=24 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=28 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=4 + local.get 2 + i32.load + i32.const 0 + i32.store + local.get 2 + i32.load + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $rbuf_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=16 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=28 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $rbuf_enqueue (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=12 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=8 + i32.const 1 + i32.add + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.rem_u + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end) + (func $rbuf_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "j\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat new file mode 100644 index 000000000..d581d9fad --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat @@ -0,0 +1,809 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + i32.const 1036 + call $slist_new + drop + i32.const 1040 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1036 + call $slist_destroy + i32.const 0 + i32.load offset=1040 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_test + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 38 + i32.add + call $slist_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 30 + i32.add + call $slist_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 22 + i32.add + call $slist_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 14 + i32.add + call $slist_add + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat new file mode 100644 index 000000000..088289953 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat @@ -0,0 +1,1124 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1044 + call $slist_add_all + drop + i32.const 8 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 4 + i32.add + call $slist_get_last + drop + local.get 0 + i32.load offset=8 + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.const 16 + i32.add + local.get 2 + i32.const 12 + i32.add + call $link_all_externally + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=12 + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=24 + i32.load offset=8 + local.get 2 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=12 + i32.store offset=8 + end + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + local.get 2 + i32.load offset=20 + i32.load + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $link_all_externally (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.const 1 + i32.const 8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@5;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.load + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=20 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load + i32.store + br 0 (;@6;) + end + end + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.load + i32.store + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=16 + i32.load + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.const 1 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat new file mode 100644 index 000000000..2093d76d3 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat @@ -0,0 +1,1336 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + i32.const 2 + call $slist_add_all_at + drop + i32.const 4 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 5 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1048 + i32.const 3 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $link_all_externally (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.const 1 + i32.const 8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=4 + block ;; label = @4 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@4;) + block ;; label = @5 + loop ;; label = @6 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@5;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.load + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=20 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load + i32.store + br 0 (;@6;) + end + end + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.load + i32.store + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=20 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@5;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=4 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@4;) + end + local.get 3 + i32.load offset=16 + i32.load + local.get 3 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=4 + i32.store + end + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.const 1 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_add_all_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=36 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.const 0 + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + local.get 3 + i32.const 24 + i32.add + local.get 3 + i32.const 28 + i32.add + call $get_node_at + i32.store offset=20 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + block ;; label = @2 + local.get 3 + i32.load offset=36 + local.get 3 + i32.const 16 + i32.add + local.get 3 + i32.const 12 + i32.add + call $link_all_externally + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=28 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.store offset=4 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=16 + i32.store offset=4 + br 1 (;@2;) + end + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.store offset=4 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + local.get 3 + i32.load offset=36 + i32.load + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat new file mode 100644 index 000000000..f7d75781a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat @@ -0,0 +1,1217 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $slist_new + drop + i32.const 1052 + call $slist_new + drop + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $slist_destroy + i32.const 0 + i32.load offset=1052 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=20 + local.get 0 + i32.load offset=20 + local.get 0 + i32.load offset=24 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=20 + i32.const 2 + call $slist_add_at + drop + i32.const 5 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 2 + local.get 0 + i32.const 16 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=20 + i32.load + local.get 0 + i32.load offset=16 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=20 + i32.const 4 + call $slist_add_at + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=20 + i32.const 0 + call $slist_add_at + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=20 + i32.load + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=20 + i32.load + local.get 0 + i32.load offset=12 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=40 + local.get 3 + local.get 1 + i32.store offset=36 + local.get 3 + local.get 2 + i32.store offset=32 + local.get 3 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.const 0 + i32.store offset=24 + local.get 3 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=32 + local.get 3 + i32.const 24 + i32.add + local.get 3 + i32.const 28 + i32.add + call $get_node_at + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + i32.const 1 + i32.const 8 + local.get 3 + i32.load offset=40 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=44 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=36 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=28 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=40 + i32.load offset=4 + i32.store offset=4 + local.get 3 + i32.load offset=40 + local.get 3 + i32.load offset=16 + i32.store offset=4 + br 1 (;@2;) + end + local.get 3 + local.get 3 + i32.load offset=28 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=28 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store offset=4 + end + local.get 3 + i32.load offset=40 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=44 + end + local.get 3 + i32.load offset=44 + local.set 2 + local.get 3 + i32.const 48 + i32.add + global.set 0 + local.get 2) + (func $get_node_at (type 6) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat new file mode 100644 index 000000000..e96c4e64a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat @@ -0,0 +1,862 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + i32.const 1040 + call $slist_new + drop + i32.const 1044 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $slist_destroy + i32.const 0 + i32.load offset=1044 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $slist_add + drop + i32.const 4 + i32.const 0 + i32.load offset=1040 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $slist_add_first + drop + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "p\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat new file mode 100644 index 000000000..ee801a815 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat @@ -0,0 +1,772 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + i32.const 1040 + call $slist_new + drop + i32.const 1044 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $slist_destroy + i32.const 0 + i32.load offset=1044 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $slist_add + drop + i32.const 4 + i32.const 0 + i32.load offset=1040 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $slist_get_last + drop + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $slist_add_last + drop + i32.const 5 + i32.const 0 + i32.load offset=1040 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 4 + i32.add + call $slist_get_last + drop + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "p\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat new file mode 100644 index 000000000..ed1ded0d9 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat @@ -0,0 +1,768 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + i32.const 1040 + call $slist_new + drop + i32.const 1044 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $slist_destroy + i32.const 0 + i32.load offset=1044 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=12 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 24 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 16 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $slist_add + drop + i32.const 2 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 20 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 12 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 8 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat new file mode 100644 index 000000000..27046f212 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat @@ -0,0 +1,1223 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $slist_copy_deep + drop + i32.const 4 + local.get 0 + i32.load offset=8 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=8 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 2 + call $slist_destroy_cb + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy_cb (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_remove_all_cb + drop + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 6) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_at (type 7) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_copy_deep (type 7) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.const 12 + i32.add + call $slist_new + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=4 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + call $slist_add + i32.store offset=8 + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + call $slist_destroy + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $copy (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + i32.load + i32.store + local.get 1 + i32.load offset=8 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $copy $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat new file mode 100644 index 000000000..62a0bb54d --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat @@ -0,0 +1,1192 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_copy_shallow + drop + i32.const 4 + local.get 0 + i32.load offset=8 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 4 + i32.add + call $slist_get_first + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + call $slist_get_first + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 4 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + call $slist_get_last + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 3 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 3 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + call $slist_destroy + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_copy_shallow (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.const 16 + i32.add + call $slist_new + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load + call $slist_add + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + call $slist_destroy + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=28 + br 3 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat new file mode 100644 index 000000000..81c50ab82 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -0,0 +1,1031 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $pred1 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $slist_filter + drop + i32.const 0 + local.get 0 + i32.load offset=8 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=4 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 4 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 12 + i32.add + call $slist_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + call $slist_add + drop + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred1 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat new file mode 100644 index 000000000..fa676bebb --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -0,0 +1,1174 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $pred2 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.ge_s + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 1052 + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1056 + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1060 + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 1064 + call $pred2 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=40 + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 40 + i32.add + call $slist_filter + drop + i32.const 2 + local.get 0 + i32.load offset=40 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=12 + local.get 0 + i32.const 0 + i32.store offset=8 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.load offset=40 + call $slist_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=8 + br_if 0 (;@3;) + local.get 0 + i32.load offset=12 + i32.load + i32.const 0 + i32.load offset=1060 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load offset=8 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.load offset=12 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load offset=8 + i32.const 1 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + i32.const 0 + sym_assert + end + local.get 0 + local.get 0 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 12 + i32.add + call $slist_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + call $slist_add + drop + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_iter_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8) + (func $slist_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=16 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred2 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat new file mode 100644 index 000000000..4b2739272 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -0,0 +1,1242 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32))) + (func $pred3 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_s + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $CHECK_EQ_LIST (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=60 + local.get 2 + local.get 1 + i32.store offset=56 + local.get 2 + i32.load offset=60 + call $slist_size + local.get 2 + i32.load offset=56 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + local.get 2 + i32.load offset=60 + local.get 2 + i32.load offset=56 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.const 16 + i32.add + local.get 2 + i32.const 12 + i32.add + local.get 2 + i32.const 8 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + br 0 (;@2;) + end + end + local.get 2 + i32.const 64 + i32.add + global.set 0) + (func $__original_main (type 5) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 1052 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1056 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1060 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 1064 + call $pred3 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $slist_filter + drop + i32.const 4 + local.get 0 + i32.load offset=8 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $CHECK_EQ_LIST + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 12 + i32.add + call $slist_new + drop + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=20 + call_indirect (type 2) + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load + call $slist_add + drop + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_zip_iter_init (type 7) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=32 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=16) + (func $slist_zip_iter_next (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=28 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=32 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred3 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat new file mode 100644 index 000000000..0c455a00a --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -0,0 +1,1096 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $pred1 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.eq + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1052 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $slist_filter_mut + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 2) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + call $unlinkn + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=8 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred1 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat new file mode 100644 index 000000000..8509b81a1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -0,0 +1,1239 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32))) + (func $pred2 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 3 + i32.ge_s + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 1052 + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1056 + call $pred2 + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1060 + call $pred2 + i32.eqz + br_if 0 (;@1;) + i32.const 1064 + call $pred2 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $slist_filter_mut + drop + i32.const 2 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=4 + local.get 0 + i32.const 0 + i32.store + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1044 + call $slist_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load + br_if 0 (;@3;) + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1060 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.load offset=4 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + sym_assert + end + block ;; label = @3 + local.get 0 + i32.load + i32.const 1 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + i32.const 0 + sym_assert + end + local.get 0 + local.get 0 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 2) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + call $unlinkn + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=8 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_iter_init (type 6) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8) + (func $slist_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=16 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred2 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat new file mode 100644 index 000000000..ea4f182fc --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -0,0 +1,1044 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $pred3 (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + i32.const 0 + i32.gt_s + i32.const 1 + i32.and) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 1052 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1056 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 1060 + call $pred3 + i32.eqz + br_if 0 (;@1;) + i32.const 1064 + call $pred3 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $slist_filter_mut + drop + i32.const 4 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_filter_mut (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + call $slist_size + br_if 0 (;@2;) + local.get 2 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 2) + br_if 0 (;@5;) + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + call $unlinkn + drop + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=8 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + br 0 (;@3;) + end + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $pred3 $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat new file mode 100644 index 000000000..cf90049a2 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat @@ -0,0 +1,955 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat new file mode 100644 index 000000000..d8d680b14 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat @@ -0,0 +1,836 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat new file mode 100644 index 000000000..25399248b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat @@ -0,0 +1,836 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat new file mode 100644 index 000000000..3182a0c98 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat @@ -0,0 +1,776 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + i32.const 1036 + call $slist_new + drop + i32.const 1040 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1036 + call $slist_destroy + i32.const 0 + i32.load offset=1040 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_test + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=12 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 8 + i32.add + call $slist_index_of + drop + i32.const 0 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + call $slist_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat new file mode 100644 index 000000000..d5340fdcd --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -0,0 +1,1453 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $slist_new + drop + i32.const 1052 + call $slist_new + drop + i32.const 0 + i32.const 1042 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $slist_destroy + i32.const 0 + i32.load offset=1052 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + call $setup_test + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=52 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=56 + i32.store + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + call $slist_iter_init + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1064 + i32.const 0 + i32.load offset=1068 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1068 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=56 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + i32.load + i32.const 0 + i32.load offset=1064 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load offset=52 + call $slist_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 5 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 3 + local.get 0 + i32.const 24 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=24 + i32.load + local.get 0 + i32.load offset=56 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + i32.const 4 + local.get 0 + i32.const 20 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=20 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.load offset=12 + local.get 0 + i32.load offset=16 + i32.store + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + call $slist_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + i32.load + i32.const 0 + i32.load offset=1068 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load offset=12 + call $slist_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 6 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 64 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8) + (func $slist_iter_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load + i32.store offset=4 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=16 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "x\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat new file mode 100644 index 000000000..3ab58e951 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -0,0 +1,1395 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1052 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1056 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1060 + i32.const 0 + i32.load offset=1064 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 40 + i32.add + call $slist_get_at + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + call $slist_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + i32.const 0 + i32.load offset=1060 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + i32.const 0 + call $slist_iter_remove + drop + end + br 0 (;@2;) + end + end + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=40 + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=40 + free + call $teardown_test + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $unlinkn (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $slist_iter_init (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8) + (func $slist_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $unlinkn + i32.store + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=16 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat new file mode 100644 index 000000000..a50ac90e5 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat @@ -0,0 +1,648 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + i32.const 1028 + call $slist_new + drop + i32.const 1032 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1028 + call $slist_destroy + i32.const 0 + i32.load offset=1032 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + local.get 0 + i32.const 0 + i32.store offset=8 + local.get 0 + i32.const 8 + i32.add + call $slist_new + drop + i32.const 0 + i32.load offset=1028 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=4 + i32.const 0 + i32.load offset=1028 + local.get 0 + i32.const 4 + i32.add + call $slist_get_first + drop + i32.const 0 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1028 + local.get 0 + i32.const 4 + i32.add + call $slist_get_last + drop + i32.const 0 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1028 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1028 + local.get 0 + i32.load offset=8 + i32.ne + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1024 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1024 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1024 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1024 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1024 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1024 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1024 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1024 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat new file mode 100644 index 000000000..c4cf11f00 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -0,0 +1,1330 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + local.set 1 + block ;; label = @1 + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1052 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1060 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + i32.load offset=1056 + i32.const 0 + i32.load offset=1064 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.const 0 + i32.load offset=1044 + i32.const 1 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + i32.const 0 + call $slist_remove + drop + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + free + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_remove (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + call $unlinkn + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_node (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=16 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 4 + i32.load offset=16 + i32.load + i32.load + local.get 4 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 4 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + br 0 (;@3;) + end + end + local.get 4 + i32.const 7 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $unlinkn (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat new file mode 100644 index 000000000..9040544e4 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat @@ -0,0 +1,912 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 1 + call $slist_remove_all_cb + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 0 + i32.store offset=8 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + local.get 0 + i32.load offset=8 + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_remove_all_cb (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $unlinkn_all + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 7 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $free $malloc $calloc) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat new file mode 100644 index 000000000..83fa2fe5c --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat @@ -0,0 +1,1179 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $slist_remove_at + drop + local.get 0 + i32.load offset=8 + free + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $slist_remove_at + drop + local.get 0 + i32.load offset=8 + free + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $unlinkn (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_remove_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + call $unlinkn + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat new file mode 100644 index 000000000..e19e4b716 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat @@ -0,0 +1,1009 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_remove_first + drop + local.get 0 + i32.load offset=8 + free + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + call $unlinkn + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat new file mode 100644 index 000000000..1457b5671 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat @@ -0,0 +1,1129 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_remove_last + drop + local.get 0 + i32.load offset=8 + free + i32.const 3 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1060 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $unlinkn (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.const 0 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 2 + i32.const 12 + i32.add + local.get 2 + i32.const 16 + i32.add + call $get_node_at + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=16 + call $unlinkn + i32.store offset=4 + block ;; label = @2 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=4 + i32.store + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat new file mode 100644 index 000000000..e0d3f1335 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat @@ -0,0 +1,1063 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1048 + call $slist_new + drop + i32.const 1052 + call $slist_new + drop + i32.const 0 + i32.const 1040 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1080 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1084 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1064 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1068 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1080 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1084 + i32.store + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $slist_destroy + i32.const 0 + i32.load offset=1052 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.load offset=4 + local.get 0 + i32.load offset=8 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + i32.const 2 + local.get 0 + call $slist_replace_at + drop + local.get 0 + i32.load + free + i32.const 0 + i32.load offset=1048 + i32.const 2 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_replace_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=40 + local.get 4 + local.get 1 + i32.store offset=36 + local.get 4 + local.get 2 + i32.store offset=32 + local.get 4 + local.get 3 + i32.store offset=28 + local.get 4 + i32.const 0 + i32.store offset=24 + local.get 4 + i32.const 0 + i32.store offset=20 + local.get 4 + local.get 4 + i32.load offset=40 + local.get 4 + i32.load offset=32 + local.get 4 + i32.const 20 + i32.add + local.get 4 + i32.const 24 + i32.add + call $get_node_at + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=16 + i32.eqz + br_if 0 (;@2;) + local.get 4 + local.get 4 + i32.load offset=16 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=20 + i32.load + i32.store offset=12 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=36 + i32.store + block ;; label = @2 + local.get 4 + i32.load offset=28 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=12 + i32.store + end + local.get 4 + i32.const 0 + i32.store offset=44 + end + local.get 4 + i32.load offset=44 + local.set 3 + local.get 4 + i32.const 48 + i32.add + global.set 0 + local.get 3) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "r\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat new file mode 100644 index 000000000..419b14735 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat @@ -0,0 +1,963 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1040 + call $slist_new + drop + i32.const 1044 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1040 + call $slist_destroy + i32.const 0 + i32.load offset=1044 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + call $setup_test + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=84 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=76 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=68 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 88 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 84 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 80 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 76 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 72 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 68 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1040 + call $slist_reverse + local.get 0 + local.get 0 + i32.load offset=68 + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store offset=36 + local.get 0 + local.get 0 + i32.load offset=76 + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=80 + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=84 + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=88 + i32.store offset=52 + local.get 0 + i32.const 8 + i32.add + i32.const 0 + i32.load offset=1040 + call $slist_iter_init + local.get 0 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.load + i32.const 2 + i32.shl + i32.add + i32.load + local.get 0 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + local.get 0 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + call $teardown_test + local.get 0 + i32.const 96 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_reverse (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=12 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=12 + i32.load + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + br 1 (;@1;) + end + local.get 1 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + local.get 1 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.store + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 1 + local.get 1 + i32.load + i32.load offset=4 + i32.store offset=4 + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.store offset=4 + local.get 1 + local.get 1 + i32.load + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.store + br 0 (;@3;) + end + end + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.store offset=4 + end) + (func $slist_iter_init (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=12 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8) + (func $slist_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=16 + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat new file mode 100644 index 000000000..a6267a6a6 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat @@ -0,0 +1,1174 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $slist_splice + drop + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1080 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 4 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_splice (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=8 + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + local.get 2 + i32.load offset=4 + i32.load + i32.add + i32.store + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat new file mode 100644 index 000000000..67287f941 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat @@ -0,0 +1,1287 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32 i32 i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + i32.const 2 + call $slist_splice_at + drop + i32.const 8 + i32.const 0 + i32.load offset=1044 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_first + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + i32.const 0 + i32.load offset=1064 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1068 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_splice_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.load + br_if 0 (;@2;) + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=16 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + call $splice_between + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $splice_between (type 7) (param i32 i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=12 + local.get 4 + local.get 1 + i32.store offset=8 + local.get 4 + local.get 2 + i32.store offset=4 + local.get 4 + local.get 3 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=12 + i32.load offset=8 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=8 + i32.load offset=8 + i32.store offset=8 + br 1 (;@2;) + end + local.get 4 + i32.load offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.load offset=8 + local.get 4 + i32.load + i32.store offset=4 + end + end + local.get 4 + i32.load offset=12 + local.tee 3 + local.get 3 + i32.load + local.get 4 + i32.load offset=8 + i32.load + i32.add + i32.store + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 4 + i32.load offset=8 + i32.const 0 + i32.store) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat new file mode 100644 index 000000000..29c574b35 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat @@ -0,0 +1,1157 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 2) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + i32.const 1 + i32.const 2 + local.get 0 + i32.const 8 + i32.add + call $slist_sublist + drop + i32.const 2 + local.get 0 + i32.load offset=8 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + i32.const 1 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + call $slist_destroy + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_sublist (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 4 + global.set 0 + local.get 4 + local.get 0 + i32.store offset=40 + local.get 4 + local.get 1 + i32.store offset=36 + local.get 4 + local.get 2 + i32.store offset=32 + local.get 4 + local.get 3 + i32.store offset=28 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 4 + i32.load offset=36 + local.get 4 + i32.load offset=32 + i32.gt_u + i32.const 1 + i32.and + br_if 0 (;@3;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=40 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 4 + i32.const 3 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + i32.const 0 + i32.store offset=24 + local.get 4 + i32.const 0 + i32.store offset=20 + local.get 4 + local.get 4 + i32.const 16 + i32.add + call $slist_new + i32.store offset=12 + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.eqz + br_if 0 (;@2;) + local.get 4 + local.get 4 + i32.load offset=12 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=40 + local.get 4 + i32.load offset=36 + local.get 4 + i32.const 20 + i32.add + local.get 4 + i32.const 24 + i32.add + call $get_node_at + i32.store offset=12 + block ;; label = @2 + local.get 4 + i32.load offset=12 + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.load offset=16 + call $slist_destroy + local.get 4 + local.get 4 + i32.load offset=12 + i32.store offset=44 + br 1 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=36 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=32 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=20 + i32.load + call $slist_add + i32.store offset=12 + block ;; label = @4 + local.get 4 + i32.load offset=12 + i32.eqz + br_if 0 (;@4;) + local.get 4 + i32.load offset=16 + call $slist_destroy + local.get 4 + local.get 4 + i32.load offset=12 + i32.store offset=44 + br 3 (;@1;) + end + local.get 4 + local.get 4 + i32.load offset=20 + i32.load offset=4 + i32.store offset=20 + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.store + local.get 4 + i32.const 0 + i32.store offset=44 + end + local.get 4 + i32.load offset=44 + local.set 3 + local.get 4 + i32.const 48 + i32.add + global.set 0 + local.get 3) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat new file mode 100644 index 000000000..c6f4744e4 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat @@ -0,0 +1,1099 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (func $setup_test (type 3) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop + i32.const 0 + i32.const 1038 + i32.symbolic + i32.store offset=1052 + i32.const 0 + i32.const 1036 + i32.symbolic + i32.store offset=1056 + i32.const 0 + i32.const 1034 + i32.symbolic + i32.store offset=1060 + i32.const 0 + i32.const 1032 + i32.symbolic + i32.store offset=1064 + i32.const 0 + i32.const 1030 + i32.symbolic + i32.store offset=1068 + i32.const 0 + i32.const 1028 + i32.symbolic + i32.store offset=1072 + i32.const 0 + i32.const 1026 + i32.symbolic + i32.store offset=1076 + i32.const 0 + i32.const 1024 + i32.symbolic + i32.store offset=1080 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1052 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1056 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1060 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1064 + i32.store + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 4 + call $malloc + i32.store offset=12 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=8 + local.get 0 + i32.const 4 + call $malloc + i32.store offset=4 + local.get 0 + i32.const 4 + call $malloc + i32.store + local.get 0 + i32.load offset=12 + i32.const 0 + i32.load offset=1068 + i32.store + local.get 0 + i32.load offset=8 + i32.const 0 + i32.load offset=1072 + i32.store + local.get 0 + i32.load offset=4 + i32.const 0 + i32.load offset=1076 + i32.store + local.get 0 + i32.load + i32.const 0 + i32.load offset=1080 + i32.store + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=12 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=8 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load offset=4 + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.load + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + global.set 0) + (func $teardown_test (type 3) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + call $setup_test + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $slist_to_array + drop + i32.const 0 + i32.load offset=1044 + i32.const 0 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 2 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load offset=8 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + i32.const 3 + local.get 0 + i32.const 4 + i32.add + call $slist_get_at + drop + local.get 0 + i32.load offset=4 + local.get 0 + i32.load offset=8 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=8 + free + call $teardown_test + local.get 0 + i32.const 16 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $get_node_at (type 5) (param i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 4 + local.get 0 + i32.store offset=24 + local.get 4 + local.get 1 + i32.store offset=20 + local.get 4 + local.get 2 + i32.store offset=16 + local.get 4 + local.get 3 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 4 + i32.load offset=20 + local.get 4 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 4 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=24 + i32.load offset=4 + i32.store + local.get 4 + i32.load offset=12 + i32.const 0 + i32.store + local.get 4 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 4 + i32.load offset=8 + local.get 4 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=16 + i32.load + i32.store + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=16 + i32.load + i32.load offset=4 + i32.store + local.get 4 + local.get 4 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 4 + i32.const 0 + i32.store offset=28 + end + local.get 4 + i32.load offset=28) + (func $slist_get_at (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 0 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + local.get 3 + i32.const 8 + i32.add + local.get 3 + i32.const 12 + i32.add + call $get_node_at + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=4 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $slist_to_array (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 2) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 2 + i32.const 0 + i32.store offset=8 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=24 + i32.load + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=12 + i32.load + i32.store + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66624)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) "@\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat new file mode 100644 index 000000000..0694e8deb --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -0,0 +1,1950 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $setup_test (type 2) + i32.const 1052 + call $slist_new + drop + i32.const 1056 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1052 + call $slist_destroy + i32.const 0 + i32.load offset=1056 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 144 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=140 + call $setup_test + local.get 0 + i32.const 1044 + i32.symbolic + i32.store offset=136 + local.get 0 + i32.load offset=136 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=136 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=136 + i32.store8 offset=134 + local.get 0 + i32.const 0 + i32.store8 offset=135 + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=128 + local.get 0 + i32.load offset=128 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=128 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=128 + i32.store8 offset=126 + local.get 0 + i32.const 0 + i32.store8 offset=127 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=112 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=128 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=80 + local.get 0 + i32.load offset=112 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=120 + local.get 0 + i32.load offset=112 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=96 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=88 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 134 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 126 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 118 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 110 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 102 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 94 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 86 + i32.add + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 126 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.const 70 + i32.add + call $slist_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_index_of + drop + i32.const 2 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 118 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_index_of + drop + i32.const 3 + local.get 0 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 78 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 70 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 5 + i32.const 0 + i32.load offset=1052 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 4 + i32.const 0 + i32.load offset=1056 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + local.get 0 + i32.const 8 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=8 + local.get 0 + i32.const 86 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 62 + i32.add + local.get 0 + i32.const 54 + i32.add + call $slist_zip_iter_add + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1056 + local.get 0 + call $slist_get_last + drop + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + call $slist_get_last + drop + local.get 0 + i32.const 110 + i32.add + local.get 0 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 144 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1048 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1048 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1048 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1048 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $slist_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $slist_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=32 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=16) + (func $slist_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=28 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=32 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $slist_zip_iter_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + i32.const 1 + i32.const 8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 1 + i32.const 8 + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load offset=24 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store offset=4 + local.get 3 + i32.load offset=24 + i32.load offset=24 + local.get 3 + i32.load offset=8 + i32.store offset=4 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=12 + i32.store offset=8 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.store offset=8 + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66608)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "y\00x\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1048) "0\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat new file mode 100644 index 000000000..3ba3482d6 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -0,0 +1,1254 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32))) + (type (;6;) (func (param i32 i32 i32) (result i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1044 + call $slist_new + drop + i32.const 1048 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1044 + call $slist_destroy + i32.const 0 + i32.load offset=1048 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 112 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=108 + call $setup_test + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=64 + local.get 0 + i32.load offset=64 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=64 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.load offset=56 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=56 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 102 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 94 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 86 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 78 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 70 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 62 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 54 + i32.add + call $slist_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + i32.const 0 + i32.load offset=1048 + call $slist_zip_iter_init + local.get 0 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + local.get 0 + i32.const 4 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + br_if 0 (;@3;) + local.get 0 + i32.const 102 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 70 + i32.add + local.get 0 + i32.load offset=4 + call $CHECK_EQUAL_C_STRING + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.const 2 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 54 + i32.add + local.get 0 + i32.load offset=4 + call $CHECK_EQUAL_C_STRING + end + local.get 0 + local.get 0 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + i32.const 3 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 112 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_zip_iter_init (type 5) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=32 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=16) + (func $slist_zip_iter_next (type 6) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=28 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=32 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $CHECK_EQUAL_C_STRING (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat new file mode 100644 index 000000000..c49f85c92 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -0,0 +1,1852 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32))) + (func $setup_test (type 2) + i32.const 1048 + call $slist_new + drop + i32.const 1052 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1048 + call $slist_destroy + i32.const 0 + i32.load offset=1052 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 144 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=140 + call $setup_test + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=136 + local.get 0 + i32.load offset=136 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=136 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=136 + i32.store8 offset=134 + local.get 0 + i32.const 0 + i32.store8 offset=135 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=128 + local.get 0 + i32.load offset=128 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=128 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=128 + i32.store8 offset=126 + local.get 0 + i32.const 0 + i32.store8 offset=127 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=128 + local.get 0 + i32.load offset=112 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=104 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=88 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + local.get 0 + i32.load offset=88 + i32.ne + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 134 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 126 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 118 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 110 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 102 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 94 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 86 + i32.add + call $slist_add + drop + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1052 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.const 24 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + local.get 0 + i32.const 126 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $slist_zip_iter_remove + drop + end + br 0 (;@2;) + end + end + local.get 0 + i32.const 126 + i32.add + local.get 0 + i32.load offset=20 + call $CHECK_EQUAL_C_STRING + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.load offset=16 + call $CHECK_EQUAL_C_STRING + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 126 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 118 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 3 + i32.const 0 + i32.load offset=1048 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 2 + i32.const 0 + i32.load offset=1052 + call $slist_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1048 + i32.const 0 + i32.load offset=1052 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.const 24 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=24 + local.get 0 + i32.const 102 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $slist_zip_iter_remove + drop + end + block ;; label = @3 + local.get 0 + i32.load offset=24 + local.get 0 + i32.const 86 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $slist_zip_iter_remove + drop + end + br 0 (;@2;) + end + end + local.get 0 + i32.const 1041 + i32.store offset=12 + local.get 0 + i32.const 1041 + i32.store offset=8 + i32.const 7 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 12 + i32.add + call $slist_get_first + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 7 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 12 + i32.add + call $slist_get_first + drop + local.get 0 + i32.const 110 + i32.add + local.get 0 + i32.load offset=12 + call $CHECK_EQUAL_C_STRING + i32.const 0 + i32.load offset=1048 + local.get 0 + i32.const 8 + i32.add + call $slist_get_last + drop + local.get 0 + i32.const 110 + i32.add + local.get 0 + i32.load offset=8 + call $CHECK_EQUAL_C_STRING + call $teardown_test + local.get 0 + i32.const 144 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1044 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1044 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1044 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1044 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $unlinkn (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.load + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + br 1 (;@1;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + end + block ;; label = @1 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@1;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 3 + i32.load offset=12 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.load + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $slist_get_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12) + (func $slist_size (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $slist_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=32 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=16) + (func $slist_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=28 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=32 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $slist_zip_iter_remove (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + local.get 3 + i32.load offset=24 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load offset=28 + call $unlinkn + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=32 + call $unlinkn + i32.store offset=8 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=24 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + block ;; label = @2 + local.get 3 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $CHECK_EQUAL_C_STRING (type 7) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1044) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat new file mode 100644 index 000000000..2eb8580e1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -0,0 +1,1704 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func)) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32) (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (type (;7;) (func (param i32 i32 i32 i32 i32) (result i32))) + (func $setup_test (type 2) + i32.const 1052 + call $slist_new + drop + i32.const 1056 + call $slist_new + drop) + (func $teardown_test (type 2) + i32.const 0 + i32.load offset=1052 + call $slist_destroy + i32.const 0 + i32.load offset=1056 + call $slist_destroy) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 160 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=156 + call $setup_test + local.get 0 + i32.const 1044 + i32.symbolic + i32.store offset=152 + local.get 0 + i32.load offset=152 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=152 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=152 + i32.store8 offset=150 + local.get 0 + i32.const 0 + i32.store8 offset=151 + local.get 0 + i32.const 1042 + i32.symbolic + i32.store offset=144 + local.get 0 + i32.load offset=144 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=144 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=144 + i32.store8 offset=142 + local.get 0 + i32.const 0 + i32.store8 offset=143 + local.get 0 + i32.const 1040 + i32.symbolic + i32.store offset=136 + local.get 0 + i32.load offset=136 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=136 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=136 + i32.store8 offset=134 + local.get 0 + i32.const 0 + i32.store8 offset=135 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=128 + local.get 0 + i32.load offset=128 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=128 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=128 + i32.store8 offset=126 + local.get 0 + i32.const 0 + i32.store8 offset=127 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=120 + local.get 0 + i32.load offset=120 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=120 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=120 + i32.store8 offset=118 + local.get 0 + i32.const 0 + i32.store8 offset=119 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=112 + local.get 0 + i32.load offset=112 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=112 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=112 + i32.store8 offset=110 + local.get 0 + i32.const 0 + i32.store8 offset=111 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=104 + local.get 0 + i32.load offset=104 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=104 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=104 + i32.store8 offset=102 + local.get 0 + i32.const 0 + i32.store8 offset=103 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=96 + local.get 0 + i32.load offset=96 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=96 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=96 + i32.store8 offset=94 + local.get 0 + i32.const 0 + i32.store8 offset=95 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.load offset=88 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=88 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=88 + i32.store8 offset=86 + local.get 0 + i32.const 0 + i32.store8 offset=87 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.load offset=80 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=80 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=80 + i32.store8 offset=78 + local.get 0 + i32.const 0 + i32.store8 offset=79 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.load offset=72 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=72 + i32.const 127 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=144 + local.get 0 + i32.load offset=152 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=144 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=144 + local.get 0 + i32.load offset=128 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=152 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=144 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=136 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=96 + local.get 0 + i32.load offset=128 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=120 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=112 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=104 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 150 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 142 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 134 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 126 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 118 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 110 + i32.add + call $slist_add + drop + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 102 + i32.add + call $slist_add + drop + local.get 0 + i32.const 32 + i32.add + i32.const 0 + i32.load offset=1052 + i32.const 0 + i32.load offset=1056 + call $slist_zip_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 28 + i32.add + local.get 0 + i32.const 24 + i32.add + call $slist_zip_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=28 + local.get 0 + i32.const 142 + i32.add + call $strcmp + br_if 0 (;@3;) + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.const 16 + i32.add + call $slist_zip_iter_replace + drop + end + br 0 (;@2;) + end + end + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 94 + i32.add + local.get 0 + i32.const 12 + i32.add + call $slist_index_of + drop + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 86 + i32.add + local.get 0 + i32.const 12 + i32.add + call $slist_index_of + drop + i32.const 1 + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1052 + local.get 0 + i32.const 94 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1056 + local.get 0 + i32.const 86 + i32.add + call $slist_contains + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_test + local.get 0 + i32.const 160 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1048 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1048 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1048 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1048 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1048 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8) + (func $slist_new (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + call $slist_conf_init + local.get 1 + local.get 1 + i32.load offset=12 + call $slist_new_conf + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $slist_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=8 + i32.load offset=4 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load + i32.store offset=12 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $slist_remove_all + drop + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=20 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $slist_remove_all (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + local.get 1 + local.get 1 + i32.load offset=8 + i32.const 0 + call $unlinkn_all + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=4 + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 1 + i32.load offset=8 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.const 7 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $unlinkn_all (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=4 + i32.store offset=12 + block ;; label = @4 + local.get 2 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=20 + call_indirect (type 1) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=24 + local.tee 1 + local.get 1 + i32.load + i32.const -1 + i32.add + i32.store + br 0 (;@3;) + end + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $slist_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $slist_add_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_add_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + i32.const 1 + i32.const 8 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 0) + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load + local.get 2 + i32.load offset=4 + i32.store + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + i32.store offset=8 + end + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $slist_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 2 + i32.load offset=4 + i32.load + local.get 2 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=4 + i32.store offset=4 + br 0 (;@2;) + end + end + local.get 2 + i32.load) + (func $slist_index_of (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.const 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 3 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + local.get 3 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + br 0 (;@3;) + end + end + local.get 3 + i32.const 8 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $slist_zip_iter_init (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.store offset=4 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=8 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=20 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=24 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=28 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.store offset=32 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.load offset=4 + i32.store offset=16) + (func $slist_zip_iter_next (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 3 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load + i32.store offset=8 + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=20 + i32.store offset=28 + end + block ;; label = @2 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=24 + i32.store offset=32 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=12 + i32.load offset=4 + i32.store offset=12 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.store + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28) + (func $slist_zip_iter_replace (type 7) (param i32 i32 i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 5 + local.get 0 + i32.store offset=24 + local.get 5 + local.get 1 + i32.store offset=20 + local.get 5 + local.get 2 + i32.store offset=16 + local.get 5 + local.get 3 + i32.store offset=12 + local.get 5 + local.get 4 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 5 + i32.load offset=24 + i32.load offset=20 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 5 + i32.load offset=24 + i32.load offset=24 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 1 (;@2;) + end + local.get 5 + i32.const 7 + i32.store offset=28 + br 1 (;@1;) + end + local.get 5 + local.get 5 + i32.load offset=24 + i32.load offset=20 + i32.load + i32.store offset=4 + local.get 5 + local.get 5 + i32.load offset=24 + i32.load offset=24 + i32.load + i32.store + local.get 5 + i32.load offset=24 + i32.load offset=20 + local.get 5 + i32.load offset=20 + i32.store + local.get 5 + i32.load offset=24 + i32.load offset=24 + local.get 5 + i32.load offset=16 + i32.store + block ;; label = @2 + local.get 5 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 5 + i32.load offset=12 + local.get 5 + i32.load offset=4 + i32.store + end + block ;; label = @2 + local.get 5 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 5 + i32.load offset=8 + local.get 5 + i32.load + i32.store + end + local.get 5 + i32.const 0 + i32.store offset=28 + end + local.get 5 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 4) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66608)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "y\00x\00i\00h\00g\00f\00e\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1048) "0\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat new file mode 100644 index 000000000..bc329d4ee --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat @@ -0,0 +1,1413 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 3) + i32.const 1036 + call $stack_new + drop) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $stack_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $stack_pop + drop + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $stack_peek + drop + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.load offset=8 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_remove_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + end + block ;; label = @2 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.const 1 + i32.sub + local.get 3 + i32.load offset=20 + i32.sub + i32.const 2 + i32.shl + i32.store offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=24 + i32.load offset=12 + local.get 3 + i32.load offset=20 + i32.const 1 + i32.add + i32.const 2 + i32.shl + i32.add + local.get 3 + i32.load offset=12 + call $memmove + drop + end + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load + i32.const -1 + i32.add + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $array_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.sub + local.get 2 + i32.load offset=8 + call $array_remove_at + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $array_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.const 1 + i32.sub + local.get 2 + i32.load offset=4 + call $array_get_at + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $memmove (type 5) (param i32 i32 i32) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 3 + local.tee 4 + local.get 0 + i32.store offset=44 + local.get 4 + local.get 1 + i32.store offset=40 + local.get 4 + local.get 2 + i32.store offset=36 + local.get 4 + local.get 4 + i32.load offset=44 + i32.store offset=32 + local.get 4 + local.get 4 + i32.load offset=40 + i32.store offset=28 + local.get 4 + i32.load offset=36 + local.set 2 + local.get 4 + local.get 3 + i32.store offset=24 + local.get 3 + local.get 2 + i32.const 15 + i32.add + i32.const -16 + i32.and + i32.sub + local.tee 3 + drop + local.get 4 + local.get 2 + i32.store offset=20 + local.get 4 + i32.const 0 + i32.store offset=16 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=16 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 3 + local.get 4 + i32.load offset=16 + i32.add + local.get 4 + i32.load offset=28 + local.get 4 + i32.load offset=16 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + br 0 (;@2;) + end + end + local.get 4 + i32.const 0 + i32.store offset=12 + block ;; label = @1 + loop ;; label = @2 + local.get 4 + i32.load offset=12 + local.get 4 + i32.load offset=36 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 4 + i32.load offset=32 + local.get 4 + i32.load offset=12 + i32.add + local.get 3 + local.get 4 + i32.load offset=12 + i32.add + i32.load8_u + i32.store8 + local.get 4 + local.get 4 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + br 0 (;@2;) + end + end + local.get 4 + i32.load offset=24 + drop + local.get 4 + i32.load offset=44) + (func $stack_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $array_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $stack_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $stack_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $stack_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $stack_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $array_new_conf + local.tee 1 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 1 + br_if 0 (;@3;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + br 1 (;@2;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $stack_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $array_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $stack_push (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $array_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $stack_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $array_get_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $stack_pop (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $array_remove_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat new file mode 100644 index 000000000..48ae167a6 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat @@ -0,0 +1,1138 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32) (result i32))) + (type (;2;) (func (param i32))) + (type (;3;) (func)) + (type (;4;) (func (result i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $setup_tests (type 3) + i32.const 1036 + call $stack_new + drop) + (func $teardown_tests (type 3) + i32.const 0 + i32.load offset=1036 + call $stack_destroy) + (func $__original_main (type 4) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=28 + call $setup_tests + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=24 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=20 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=16 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 24 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $stack_peek + drop + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 20 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $stack_peek + drop + local.get 0 + i32.const 20 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 16 + i32.add + call $stack_push + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 12 + i32.add + call $stack_peek + drop + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + sym_assert + call $teardown_tests + local.get 0 + i32.const 32 + i32.add + global.set 0 + i32.const 0) + (func $array_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + f32.const 0x1p+1 (;=2;) + f32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 8 + i32.store + local.get 1 + i32.load offset=12 + i32.const 1 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=16) + (func $array_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.const 0x1p+0 (;=1;) + f32.le + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + f32.const 0x1p+1 (;=2;) + f32.store offset=16 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + f32.load offset=4 + f32.store offset=16 + end + block ;; label = @1 + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + f32.load offset=16 + i32.const 16777216 + local.get 2 + i32.load offset=24 + i32.load + i32.div_u + f32.convert_i32_u + f32.ge + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + end + local.get 2 + i32.const 2 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.const 2 + i32.shl + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 1) + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=12 + local.get 2 + f32.load offset=16 + f32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=20 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=24 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $array_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $array_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + call $expand_capacity + i32.store + block ;; label = @3 + local.get 2 + i32.load + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + br 2 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + i32.add + local.get 2 + i32.load offset=4 + i32.store + local.get 2 + i32.load offset=8 + local.tee 1 + local.get 1 + i32.load + i32.const 1 + i32.add + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $expand_capacity (type 1) (param i32) (result i32) + (local i32 f32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.const 16777216 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 1 + i32.const 4 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=8 + local.tee 0 + i32.load offset=4 + f32.convert_i32_u + local.get 0 + f32.load offset=8 + f32.mul + local.tee 2 + f32.const 0x1p+32 (;=4.29497e+09;) + f32.lt + local.get 2 + f32.const 0x0p+0 (;=0;) + f32.ge + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.trunc_f32_u + local.set 0 + br 1 (;@2;) + end + i32.const 0 + local.set 0 + end + local.get 1 + local.get 0 + i32.store offset=4 + block ;; label = @2 + block ;; label = @3 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=8 + i32.load offset=4 + i32.le_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 1 + i32.load offset=8 + i32.const 16777216 + i32.store offset=4 + br 1 (;@2;) + end + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=4 + i32.store offset=4 + end + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 2 + i32.shl + local.get 1 + i32.load offset=8 + i32.load offset=16 + call_indirect (type 1) + i32.store + block ;; label = @2 + local.get 1 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 1 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 1 + i32.load + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load + i32.const 2 + i32.shl + call $memcpy + drop + local.get 1 + i32.load offset=8 + i32.load offset=12 + local.get 1 + i32.load offset=8 + i32.load offset=24 + call_indirect (type 2) + local.get 1 + i32.load offset=8 + local.get 1 + i32.load + i32.store offset=12 + local.get 1 + i32.const 0 + i32.store offset=12 + end + local.get 1 + i32.load offset=12 + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $array_get_at (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load + i32.ge_u + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 8 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.const 2 + i32.shl + i32.add + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12) + (func $array_get_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load + br_if 0 (;@2;) + local.get 2 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.const 1 + i32.sub + local.get 2 + i32.load offset=4 + call $array_get_at + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $memcpy (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=28 + local.get 3 + local.get 1 + i32.store offset=24 + local.get 3 + local.get 2 + i32.store offset=20 + local.get 3 + local.get 3 + i32.load offset=28 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 3 + i32.const 0 + i32.store offset=16 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=20 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=8 + i32.load8_u + i32.store8 + local.get 3 + local.get 3 + i32.load offset=16 + i32.const 1 + i32.add + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 3 + i32.load offset=28) + (func $stack_conf_init (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $array_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $stack_new (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=28 + local.get 1 + i32.const 8 + i32.add + call $stack_conf_init + local.get 1 + i32.const 8 + i32.add + local.get 1 + i32.load offset=28 + call $stack_new_conf + local.set 0 + local.get 1 + i32.const 32 + i32.add + global.set 0 + local.get 0) + (func $stack_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $array_new_conf + local.tee 1 + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 1 + br_if 0 (;@3;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + br 1 (;@2;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $stack_destroy (type 2) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $array_destroy + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=12 + call_indirect (type 2) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $stack_push (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $array_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $stack_peek (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $array_get_last + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $assert (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 2) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 1) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 4 4 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat new file mode 100644 index 000000000..fcba91398 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -0,0 +1,1603 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_add + drop + i32.const 3 + i32.const 0 + i32.load offset=1036 + call $treeset_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $treetable_contains_key + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat new file mode 100644 index 000000000..ada499512 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -0,0 +1,1821 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=44 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 56 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 52 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 48 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 44 + i32.add + call $treeset_add + drop + local.get 0 + i32.const 0 + i32.store offset=40 + local.get 0 + i32.const 0 + i32.store offset=36 + local.get 0 + i32.const 0 + i32.store offset=32 + local.get 0 + i32.const 0 + i32.store offset=28 + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1036 + call $treeset_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $treeset_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=56 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=40 + i32.const 1 + i32.add + i32.store offset=40 + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=52 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=36 + i32.const 1 + i32.add + i32.store offset=36 + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=48 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=32 + i32.const 1 + i32.add + i32.store offset=32 + end + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=44 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=28 + i32.const 1 + i32.add + i32.store offset=28 + end + br 0 (;@2;) + end + end + i32.const 1 + local.get 0 + i32.load offset=40 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + call $treetable_iter_init + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treeset_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_iter_next + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $get_successor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + call $tree_min + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=20 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + local.set 1 + local.get 2 + i32.load offset=12 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $get_successor_node + local.set 1 + local.get 2 + i32.load offset=8 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "d\00c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat new file mode 100644 index 000000000..499a94143 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -0,0 +1,2683 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=36 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=32 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=32 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 40 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 32 + i32.add + call $treeset_add + drop + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1036 + call $treeset_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 12 + i32.add + call $treeset_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + i32.const 16 + i32.add + i32.const 0 + call $treeset_iter_remove + drop + end + br 0 (;@2;) + end + end + i32.const 2 + i32.const 0 + i32.load offset=1036 + call $treeset_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 36 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $treetable_contains_key + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $treeset_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load + call $treetable_iter_init + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treeset_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_iter_next + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $treetable_iter_remove + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $get_successor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + call $tree_min + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=20 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $remove_node (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + local.set 1 + local.get 2 + i32.load offset=12 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $get_successor_node + local.set 1 + local.get 2 + i32.load offset=8 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 6 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load offset=4 + i32.store + end + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $remove_node + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat new file mode 100644 index 000000000..82fe3150f --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -0,0 +1,2383 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + i32.const 0 + call $treeset_remove + drop + i32.const 2 + i32.const 0 + i32.load offset=1036 + call $treeset_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_remove (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=8 + local.get 3 + local.get 1 + i32.store offset=4 + local.get 3 + local.get 2 + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=4 + local.get 3 + i32.load + call $treetable_remove + i32.const 6 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.const 7 + i32.store offset=12 + br 1 (;@1;) + end + local.get 3 + i32.const 0 + i32.store offset=12 + end + local.get 3 + i32.load offset=12 + local.set 2 + local.get 3 + i32.const 16 + i32.add + global.set 0 + local.get 2) + (func $treeset_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $treetable_contains_key + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_remove (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_tree_node_by_key + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 6 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $remove_node + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $remove_node (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat new file mode 100644 index 000000000..8d4fc3dc0 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -0,0 +1,1708 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + call $treeset_remove_all + i32.const 0 + i32.const 0 + i32.load offset=1036 + call $treeset_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_contains + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_remove_all (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_remove_all + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_contains (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + call $treetable_contains_key + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_remove_all (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.store + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat new file mode 100644 index 000000000..61eb6ff92 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -0,0 +1,1382 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32 i32) (result i32))) + (type (;5;) (func (param i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=12 + i32.const 1 + i32.const 1036 + call $treeset_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=8 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=4 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=8 + local.get 0 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=4 + local.get 0 + i32.load + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 8 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + i32.const 4 + i32.add + call $treeset_add + drop + i32.const 0 + i32.load offset=1036 + local.get 0 + call $treeset_add + drop + i32.const 3 + i32.const 0 + i32.load offset=1036 + call $treeset_size + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + local.set 1 + local.get 0 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1032 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1032 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1032 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1032 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1032 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + call $treetable_conf_init + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treeset_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treeset_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treeset_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 20 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + local.get 2 + i32.const 12 + i32.add + call $treetable_new_conf + i32.store offset=8 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + local.get 2 + i32.load offset=8 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + i32.const 1 + i32.store offset=4 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=16 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treeset_add (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + i32.load + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + call $treetable_add + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treeset_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $treetable_size + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_add (type 4) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 5) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66576)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "c\00b\00a\00") + (data (;1;) (i32.const 1032) "\10\04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat new file mode 100644 index 000000000..9541b834b --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -0,0 +1,1491 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + i32.const 1 + i32.const 1040 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=24 + i32.lt_s + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.load offset=24 + local.get 0 + i32.load offset=16 + i32.lt_s + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 1 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 44 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $treetable_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat new file mode 100644 index 000000000..f0093eaf7 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -0,0 +1,1585 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + i32.const 1 + i32.const 1040 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 16 + i32.add + call $treetable_get + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 12 + i32.add + call $treetable_get + drop + local.get 0 + i32.load offset=16 + local.get 0 + i32.const 30 + i32.add + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + local.get 0 + i32.load offset=12 + local.get 0 + i32.const 22 + i32.add + call $strcmp + i32.const 0 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $treetable_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $strcmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 0 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=8 + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.const 0 + i32.store offset=20 + block ;; label = @2 + loop ;; label = @3 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.eqz + br_if 1 (;@2;) + block ;; label = @4 + local.get 2 + i32.load offset=12 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + local.get 2 + i32.load offset=8 + i32.load8_u + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.const 1 + i32.store offset=16 + end + local.get 2 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.add + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + br 0 (;@3;) + end + end + end + local.get 2 + i32.load offset=16) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_get (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_tree_node_by_key + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 6 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat new file mode 100644 index 000000000..05ab0e1e1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -0,0 +1,1459 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $treetable_get_first_key + drop + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_get_first_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 6 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat new file mode 100644 index 000000000..0683c656e --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -0,0 +1,1707 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 8 + i32.add + call $treetable_get_greater_than + drop + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_get_greater_than (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_tree_node_by_key + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $get_successor_node + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 6 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_successor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + call $tree_min + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=20 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat new file mode 100644 index 000000000..904724930 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -0,0 +1,1459 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 8 + i32.add + call $treetable_get_last_key + drop + local.get 0 + i32.load offset=44 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $tree_max (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_get_last_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_max + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load + i32.store + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 6 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat new file mode 100644 index 000000000..435bae4f1 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -0,0 +1,1707 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 8 + i32.add + call $treetable_get_lesser_than + drop + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=8 + i32.load + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_max (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_get_lesser_than (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_tree_node_by_key + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $get_predecessor_node + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=8 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=8 + i32.load + i32.store + local.get 3 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.const 6 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $get_predecessor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + call $tree_max + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=16 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat new file mode 100644 index 000000000..ad4f85eda --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -0,0 +1,1750 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 96 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=92 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=88 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=84 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=80 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=76 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=88 + local.get 0 + i32.load offset=84 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=84 + local.get 0 + i32.load offset=76 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=76 + local.get 0 + i32.load offset=80 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=72 + local.get 0 + local.get 0 + i32.load offset=72 + i32.store8 offset=70 + local.get 0 + i32.const 0 + i32.store8 offset=71 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=64 + local.get 0 + local.get 0 + i32.load offset=64 + i32.store8 offset=62 + local.get 0 + i32.const 0 + i32.store8 offset=63 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=56 + local.get 0 + local.get 0 + i32.load offset=56 + i32.store8 offset=54 + local.get 0 + i32.const 0 + i32.store8 offset=55 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=48 + local.get 0 + local.get 0 + i32.load offset=48 + i32.store8 offset=46 + local.get 0 + i32.const 0 + i32.store8 offset=47 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 80 + i32.add + local.get 0 + i32.const 70 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 76 + i32.add + local.get 0 + i32.const 62 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 84 + i32.add + local.get 0 + i32.const 54 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 88 + i32.add + local.get 0 + i32.const 46 + i32.add + call $treetable_add + drop + local.get 0 + i32.const 0 + i32.store offset=40 + local.get 0 + i32.const 0 + i32.store offset=36 + local.get 0 + i32.const 0 + i32.store offset=32 + local.get 0 + i32.const 0 + i32.store offset=28 + local.get 0 + i32.const 16 + i32.add + i32.const 0 + i32.load offset=1044 + call $treetable_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 16 + i32.add + local.get 0 + i32.const 8 + i32.add + call $treetable_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + local.get 0 + i32.load offset=8 + i32.store offset=4 + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load offset=88 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=40 + i32.const 1 + i32.add + i32.store offset=40 + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load offset=84 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=36 + i32.const 1 + i32.add + i32.store offset=36 + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load offset=80 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=32 + i32.const 1 + i32.add + i32.store offset=32 + end + block ;; label = @3 + local.get 0 + i32.load offset=4 + i32.load + local.get 0 + i32.load offset=76 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 0 + local.get 0 + i32.load offset=28 + i32.const 1 + i32.add + i32.store offset=28 + end + br 0 (;@2;) + end + end + i32.const 1 + local.get 0 + i32.load offset=40 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=36 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=32 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 1 + local.get 0 + i32.load offset=28 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=92 + local.set 1 + local.get 0 + i32.const 96 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $get_successor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + call $tree_min + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=20 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + local.set 1 + local.get 2 + i32.load offset=12 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $get_successor_node + local.set 1 + local.get 2 + i32.load offset=8 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat new file mode 100644 index 000000000..cd6954924 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -0,0 +1,2532 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 80 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=76 + i32.const 1 + i32.const 1040 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=72 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=68 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=64 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=72 + local.get 0 + i32.load offset=68 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=68 + local.get 0 + i32.load offset=64 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=60 + local.get 0 + local.get 0 + i32.load offset=60 + i32.store8 offset=58 + local.get 0 + i32.const 0 + i32.store8 offset=59 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=52 + local.get 0 + local.get 0 + i32.load offset=52 + i32.store8 offset=50 + local.get 0 + i32.const 0 + i32.store8 offset=51 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + local.get 0 + i32.load offset=44 + i32.store8 offset=42 + local.get 0 + i32.const 0 + i32.store8 offset=43 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 72 + i32.add + local.get 0 + i32.const 58 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 68 + i32.add + local.get 0 + i32.const 50 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 64 + i32.add + local.get 0 + i32.const 42 + i32.add + call $treetable_add + drop + local.get 0 + i32.const 24 + i32.add + i32.const 0 + i32.load offset=1040 + call $treetable_iter_init + block ;; label = @1 + loop ;; label = @2 + local.get 0 + i32.const 24 + i32.add + local.get 0 + i32.const 16 + i32.add + call $treetable_iter_next + i32.const 9 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 0 + local.get 0 + i32.load offset=16 + i32.store offset=12 + block ;; label = @3 + local.get 0 + i32.load offset=12 + i32.load + local.get 0 + i32.load offset=68 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + i32.const 0 + local.get 0 + i32.const 24 + i32.add + i32.const 0 + call $treetable_iter_remove + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 6 + local.get 0 + i32.const 24 + i32.add + i32.const 0 + call $treetable_iter_remove + i32.eq + i32.const 1 + i32.and + sym_assert + end + br 0 (;@2;) + end + end + i32.const 2 + i32.const 0 + i32.load offset=1040 + call $treetable_size + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 68 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $treetable_destroy + local.get 0 + i32.load offset=76 + local.set 1 + local.get 0 + i32.const 80 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $get_successor_node (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + call $tree_min + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=4 + i32.load offset=12 + i32.store + loop ;; label = @2 + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=20 + i32.eq + local.set 1 + end + block ;; label = @3 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load + i32.store offset=4 + local.get 2 + local.get 2 + i32.load + i32.load offset=12 + i32.store + br 1 (;@2;) + end + end + local.get 2 + local.get 2 + i32.load + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $remove_node (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_init (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.store + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + local.set 1 + local.get 2 + i32.load offset=12 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_iter_next (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 9 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load offset=4 + i32.store offset=4 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.load + i32.store + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=8 + i32.store offset=4 + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $get_successor_node + local.set 1 + local.get 2 + i32.load offset=8 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_iter_remove (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 6 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=4 + i32.load offset=4 + i32.store + end + local.get 2 + i32.load offset=8 + i32.load + local.get 2 + i32.load offset=8 + i32.load offset=4 + call $remove_node + local.get 2 + i32.load offset=8 + i32.const 0 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat new file mode 100644 index 000000000..551f338cc --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -0,0 +1,2244 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=28 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=8 + local.get 0 + local.get 0 + i32.load offset=8 + i32.store8 offset=6 + local.get 0 + i32.const 0 + i32.store8 offset=7 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=40 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=32 + local.get 0 + i32.load offset=36 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 6 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + i32.const 0 + call $treetable_remove + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 32 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_remove (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=20 + call $get_tree_node_by_key + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 6 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 3 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=16 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.store + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load offset=12 + call $remove_node + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $remove_node (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat new file mode 100644 index 000000000..7a6e19787 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat @@ -0,0 +1,1517 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=12 + local.get 0 + local.get 0 + i32.load offset=12 + i32.store8 offset=10 + local.get 0 + i32.const 0 + i32.store8 offset=11 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 26 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 18 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + local.get 0 + i32.const 10 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + call $treetable_remove_all + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 40 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 36 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.const 48 + i32.add + global.set 0 + i32.const 0) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $treetable_remove_all (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store offset=8 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=4 + i32.store + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat new file mode 100644 index 000000000..5b25cda87 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -0,0 +1,2268 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + i32.const 0 + call $treetable_remove_first + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $remove_node (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_remove_first (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 6 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_min + i32.store + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=4 + i32.store + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + call $remove_node + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat new file mode 100644 index 000000000..c043c5e18 --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -0,0 +1,2309 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (type (;6;) (func (param i32 i32 i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 64 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=60 + i32.const 1 + i32.const 1044 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=56 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=52 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=48 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=44 + local.get 0 + i32.const 1038 + i32.symbolic + i32.store offset=40 + local.get 0 + local.get 0 + i32.load offset=40 + i32.store8 offset=38 + local.get 0 + i32.const 0 + i32.store8 offset=39 + local.get 0 + i32.const 1036 + i32.symbolic + i32.store offset=32 + local.get 0 + local.get 0 + i32.load offset=32 + i32.store8 offset=30 + local.get 0 + i32.const 0 + i32.store8 offset=31 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=24 + local.get 0 + local.get 0 + i32.load offset=24 + i32.store8 offset=22 + local.get 0 + i32.const 0 + i32.store8 offset=23 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=16 + local.get 0 + local.get 0 + i32.load offset=16 + i32.store8 offset=14 + local.get 0 + i32.const 0 + i32.store8 offset=15 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=56 + local.get 0 + i32.load offset=52 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=52 + local.get 0 + i32.load offset=48 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=48 + local.get 0 + i32.load offset=44 + i32.lt_s + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 48 + i32.add + local.get 0 + i32.const 38 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + local.get 0 + i32.const 30 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 52 + i32.add + local.get 0 + i32.const 22 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 56 + i32.add + local.get 0 + i32.const 14 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1044 + i32.const 0 + call $treetable_remove_last + drop + i32.const 0 + i32.const 0 + i32.load offset=1044 + local.get 0 + i32.const 44 + i32.add + call $treetable_contains_key + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1044 + call $treetable_destroy + local.get 0 + i32.load offset=60 + local.set 1 + local.get 0 + i32.const 64 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1040 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1040 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1040 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1040 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1040 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $get_tree_node_by_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=8 + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + loop ;; label = @2 + local.get 2 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.load + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=16 + i32.store offset=16 + br 1 (;@3;) + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=8 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=16 + br 1 (;@4;) + end + local.get 2 + local.get 2 + i32.load offset=16 + i32.store offset=28 + br 3 (;@1;) + end + end + i32.const 0 + local.set 1 + block ;; label = @3 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.const 0 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + br_if 0 (;@2;) + end + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $tree_min (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $tree_max (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + local.get 2 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=8) + (func $treetable_contains_key (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + call $get_tree_node_by_key + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=12 + br 1 (;@1;) + end + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $remove_node (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + local.get 2 + i32.load offset=24 + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $transplant + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=24 + i32.load offset=20 + local.get 2 + i32.load offset=28 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=20 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=24 + i32.load offset=16 + call $transplant + br 1 (;@2;) + end + local.get 2 + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + i32.load offset=20 + call $tree_min + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.store offset=12 + local.get 2 + local.get 2 + i32.load offset=16 + i32.load offset=20 + i32.store offset=20 + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=16 + i32.load offset=12 + local.get 2 + i32.load offset=24 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + br 1 (;@3;) + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=20 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=20 + i32.store offset=20 + local.get 2 + i32.load offset=16 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store offset=12 + end + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=16 + call $transplant + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=16 + i32.store offset=16 + local.get 2 + i32.load offset=16 + i32.load offset=16 + local.get 2 + i32.load offset=16 + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load8_u offset=8 + i32.store8 offset=8 + end + end + block ;; label = @1 + local.get 2 + i32.load offset=12 + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=28 + local.get 2 + i32.load offset=20 + call $rebalance_after_delete + end + local.get 2 + i32.load offset=24 + local.get 2 + i32.load offset=28 + i32.load offset=24 + call_indirect (type 1) + local.get 2 + i32.load offset=28 + local.tee 1 + local.get 1 + i32.load offset=8 + i32.const -1 + i32.add + i32.store offset=8 + local.get 2 + i32.const 32 + i32.add + global.set 0) + (func $transplant (type 6) (param i32 i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 3 + local.get 0 + i32.store offset=12 + local.get 3 + local.get 1 + i32.store offset=8 + local.get 3 + local.get 2 + i32.store offset=4 + block ;; label = @1 + block ;; label = @2 + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 3 + i32.load offset=8 + i32.load offset=12 + local.get 3 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 3 + i32.load offset=4 + local.get 3 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12) + (func $rebalance_after_delete (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + loop ;; label = @1 + i32.const 0 + local.set 1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=8 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + local.set 1 + end + block ;; label = @2 + local.get 1 + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@4;) + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + i32.const 1 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + call $rotate_left + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + call $rotate_right + local.get 2 + local.get 2 + i32.load offset=12 + i32.load + i32.store offset=8 + end + end + br 1 (;@1;) + end + end + local.get 2 + i32.load offset=8 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_remove_last (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=8 + local.get 2 + local.get 1 + i32.store offset=4 + local.get 2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load + call $tree_max + i32.store + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 6 + i32.store offset=12 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=4 + i32.const 0 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=4 + local.get 2 + i32.load + i32.load offset=4 + i32.store + end + local.get 2 + i32.load offset=8 + local.get 2 + i32.load + call $remove_node + local.get 2 + i32.const 0 + i32.store offset=12 + end + local.get 2 + i32.load offset=12 + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00w\00d\00c\00b\00a\00") + (data (;1;) (i32.const 1040) " \04\01\00")) \ No newline at end of file diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat new file mode 100644 index 000000000..28bf452fd --- /dev/null +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -0,0 +1,1343 @@ +(module + (type (;0;) (func (param i32 i32) (result i32))) + (type (;1;) (func (param i32))) + (type (;2;) (func (param i32) (result i32))) + (type (;3;) (func (result i32))) + (type (;4;) (func (param i32 i32))) + (type (;5;) (func (param i32 i32 i32) (result i32))) + (func $__original_main (type 3) (result i32) + (local i32 i32) + global.get 0 + i32.const 48 + i32.sub + local.tee 0 + global.set 0 + local.get 0 + i32.const 0 + i32.store offset=44 + i32.const 1 + i32.const 1040 + call $treetable_new + drop + local.get 0 + i32.const 1028 + i32.symbolic + i32.store offset=40 + local.get 0 + i32.const 1026 + i32.symbolic + i32.store offset=36 + local.get 0 + i32.const 1024 + i32.symbolic + i32.store offset=32 + local.get 0 + i32.const 1034 + i32.symbolic + i32.store offset=28 + local.get 0 + local.get 0 + i32.load offset=28 + i32.store8 offset=26 + local.get 0 + i32.const 0 + i32.store8 offset=27 + local.get 0 + i32.const 1032 + i32.symbolic + i32.store offset=20 + local.get 0 + local.get 0 + i32.load offset=20 + i32.store8 offset=18 + local.get 0 + i32.const 0 + i32.store8 offset=19 + local.get 0 + i32.const 1030 + i32.symbolic + i32.store offset=12 + local.get 0 + local.get 0 + i32.load offset=12 + i32.store8 offset=10 + local.get 0 + i32.const 0 + i32.store8 offset=11 + i32.const 0 + local.set 1 + block ;; label = @1 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=36 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + i32.const 0 + local.set 1 + local.get 0 + i32.load offset=40 + local.get 0 + i32.load offset=32 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 0 + i32.load offset=36 + local.get 0 + i32.load offset=32 + i32.ne + local.set 1 + end + local.get 1 + i32.const 1 + i32.and + sym_assume + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 40 + i32.add + local.get 0 + i32.const 26 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 36 + i32.add + local.get 0 + i32.const 18 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + local.get 0 + i32.const 32 + i32.add + local.get 0 + i32.const 10 + i32.add + call $treetable_add + drop + i32.const 0 + i32.load offset=1040 + call $treetable_size + i32.const 3 + i32.eq + i32.const 1 + i32.and + sym_assert + i32.const 0 + i32.load offset=1040 + call $treetable_destroy + local.get 0 + i32.load offset=44 + local.set 1 + local.get 0 + i32.const 48 + i32.add + global.set 0 + local.get 1) + (func $malloc (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.const 0 + i32.load offset=1036 + i32.store offset=8 + local.get 1 + i32.const 0 + i32.store offset=4 + block ;; label = @1 + loop ;; label = @2 + local.get 1 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=4 + i32.add + i32.const 105 + i32.store8 + local.get 1 + local.get 1 + i32.load offset=4 + i32.const 1 + i32.add + i32.store offset=4 + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 1 + i32.load offset=12 + i32.add + i32.store offset=1036 + local.get 1 + i32.load offset=8 + local.get 1 + i32.load offset=12 + alloc + local.set 0 + local.get 1 + i32.const 16 + i32.add + global.set 0 + local.get 0) + (func $calloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.const 0 + i32.load offset=1036 + i32.store offset=4 + local.get 2 + i32.const 0 + i32.store + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.lt_u + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@1;) + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load + i32.add + i32.const 0 + i32.store8 + local.get 2 + local.get 2 + i32.load + i32.const 1 + i32.add + i32.store + br 0 (;@2;) + end + end + i32.const 0 + i32.const 0 + i32.load offset=1036 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + i32.add + i32.store offset=1036 + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.mul + alloc + local.set 1 + local.get 2 + i32.const 16 + i32.add + global.set 0 + local.get 1) + (func $free (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + free + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $treetable_conf_init (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 2 + i32.store offset=4 + local.get 1 + i32.load offset=12 + i32.const 3 + i32.store offset=8 + local.get 1 + i32.load offset=12 + i32.const 4 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.const 0 + i32.store) + (func $treetable_new (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=28 + local.get 2 + local.get 1 + i32.store offset=24 + local.get 2 + i32.const 8 + i32.add + call $treetable_conf_init + local.get 2 + local.get 2 + i32.load offset=28 + i32.store offset=8 + local.get 2 + i32.const 8 + i32.add + local.get 2 + i32.load offset=24 + call $treetable_new_conf + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_new_conf (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + i32.const 1 + i32.const 28 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=16 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.const 24 + local.get 2 + i32.load offset=24 + i32.load offset=8 + call_indirect (type 0) + i32.store offset=12 + block ;; label = @2 + local.get 2 + i32.load offset=12 + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 1) + local.get 2 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=16 + i32.const 0 + i32.store offset=8 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=12 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=24 + i32.load offset=12 + i32.store offset=24 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.store offset=4 + local.get 2 + i32.load offset=20 + local.get 2 + i32.load offset=16 + i32.store + local.get 2 + i32.const 0 + i32.store offset=28 + end + local.get 2 + i32.load offset=28 + local.set 1 + local.get 2 + i32.const 32 + i32.add + global.set 0 + local.get 1) + (func $treetable_destroy (type 1) (param i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + global.set 0 + local.get 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load + call $tree_destroy + local.get 1 + i32.load offset=12 + i32.load offset=4 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.load offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + local.get 1 + i32.const 16 + i32.add + global.set 0) + (func $tree_destroy (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + br 1 (;@1;) + end + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=16 + call $tree_destroy + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=20 + call $tree_destroy + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=12 + i32.load offset=24 + call_indirect (type 1) + end + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $treetable_size (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12 + i32.load offset=8) + (func $treetable_add (type 5) (param i32 i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 3 + global.set 0 + local.get 3 + local.get 0 + i32.store offset=24 + local.get 3 + local.get 1 + i32.store offset=20 + local.get 3 + local.get 2 + i32.store offset=16 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=12 + local.get 3 + local.get 3 + i32.load offset=24 + i32.load + i32.store offset=8 + block ;; label = @1 + block ;; label = @2 + loop ;; label = @3 + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 1 (;@2;) + local.get 3 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=8 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.store offset=4 + local.get 3 + local.get 3 + i32.load offset=8 + i32.store offset=12 + block ;; label = @4 + block ;; label = @5 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=16 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + block ;; label = @6 + local.get 3 + i32.load offset=4 + i32.const 0 + i32.gt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 3 + local.get 3 + i32.load offset=8 + i32.load offset=20 + i32.store offset=8 + br 1 (;@5;) + end + local.get 3 + i32.load offset=8 + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.const 0 + i32.store offset=28 + br 4 (;@1;) + end + end + br 0 (;@3;) + end + end + local.get 3 + i32.const 24 + local.get 3 + i32.load offset=24 + i32.load offset=16 + call_indirect (type 2) + i32.store + block ;; label = @2 + local.get 3 + i32.load + i32.const 0 + i32.ne + i32.const 1 + i32.and + br_if 0 (;@2;) + local.get 3 + i32.const 1 + i32.store offset=28 + br 1 (;@1;) + end + local.get 3 + i32.load + local.get 3 + i32.load offset=16 + i32.store offset=4 + local.get 3 + i32.load + local.get 3 + i32.load offset=20 + i32.store + local.get 3 + i32.load + local.get 3 + i32.load offset=12 + i32.store offset=12 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=16 + local.get 3 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.store offset=20 + local.get 3 + i32.load offset=24 + local.tee 2 + local.get 2 + i32.load offset=8 + i32.const 1 + i32.add + i32.store offset=8 + block ;; label = @2 + block ;; label = @3 + local.get 3 + i32.load offset=12 + local.get 3 + i32.load offset=24 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + i32.store + local.get 3 + i32.load + i32.const 1 + i32.store8 offset=8 + br 1 (;@2;) + end + local.get 3 + i32.load + i32.const 0 + i32.store8 offset=8 + block ;; label = @3 + block ;; label = @4 + local.get 3 + i32.load offset=20 + local.get 3 + i32.load offset=12 + i32.load + local.get 3 + i32.load offset=24 + i32.load offset=12 + call_indirect (type 0) + i32.const 0 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=16 + br 1 (;@3;) + end + local.get 3 + i32.load offset=12 + local.get 3 + i32.load + i32.store offset=20 + end + local.get 3 + i32.load offset=24 + local.get 3 + i32.load + call $rebalance_after_insert + end + local.get 3 + i32.const 0 + i32.store offset=28 + end + local.get 3 + i32.load offset=28 + local.set 2 + local.get 3 + i32.const 32 + i32.add + global.set 0 + local.get 2) + (func $rebalance_after_insert (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + global.set 0 + local.get 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + block ;; label = @1 + loop ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 1 (;@1;) + block ;; label = @3 + block ;; label = @4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@4;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=20 + i32.store offset=4 + block ;; label = @5 + block ;; label = @6 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@6;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@5;) + end + block ;; label = @6 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@6;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_left + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_right + end + br 1 (;@3;) + end + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.load offset=16 + i32.store offset=4 + block ;; label = @4 + block ;; label = @5 + local.get 2 + i32.load offset=4 + i32.load8_u offset=8 + i32.const 24 + i32.shl + i32.const 24 + i32.shr_s + br_if 0 (;@5;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=4 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.store offset=8 + br 1 (;@4;) + end + block ;; label = @5 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@5;) + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + call $rotate_right + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + i32.const 0 + i32.store8 offset=8 + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=12 + call $rotate_left + end + end + br 0 (;@2;) + end + end + local.get 2 + i32.load offset=12 + i32.load + i32.const 1 + i32.store8 offset=8 + local.get 2 + i32.const 16 + i32.add + global.set 0) + (func $rotate_left (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=20 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=16 + i32.store offset=20 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=16 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=16 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=16 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $rotate_right (type 4) (param i32 i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + local.get 2 + i32.load offset=8 + i32.load offset=16 + i32.store offset=4 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.load offset=20 + i32.store offset=16 + block ;; label = @1 + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.ne + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@1;) + local.get 2 + i32.load offset=4 + i32.load offset=20 + local.get 2 + i32.load offset=8 + i32.store offset=12 + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=12 + i32.load offset=4 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store + br 1 (;@1;) + end + block ;; label = @2 + block ;; label = @3 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=8 + i32.load offset=12 + i32.load offset=20 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@3;) + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=20 + br 1 (;@2;) + end + local.get 2 + i32.load offset=8 + i32.load offset=12 + local.get 2 + i32.load offset=4 + i32.store offset=16 + end + end + local.get 2 + i32.load offset=4 + local.get 2 + i32.load offset=8 + i32.store offset=20 + local.get 2 + i32.load offset=8 + local.get 2 + i32.load offset=4 + i32.store offset=12) + (func $cmp (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 32 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=24 + local.get 2 + local.get 1 + i32.store offset=20 + local.get 2 + local.get 2 + i32.load offset=24 + i32.load + i32.store offset=16 + local.get 2 + local.get 2 + i32.load offset=20 + i32.load + i32.store offset=12 + block ;; label = @1 + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.lt_s + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const -1 + i32.store offset=28 + br 1 (;@1;) + end + block ;; label = @2 + local.get 2 + i32.load offset=16 + local.get 2 + i32.load offset=12 + i32.eq + i32.const 1 + i32.and + i32.eqz + br_if 0 (;@2;) + local.get 2 + i32.const 0 + i32.store offset=28 + br 1 (;@1;) + end + local.get 2 + i32.const 1 + i32.store offset=28 + end + local.get 2 + i32.load offset=28) + (func $assume (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $assert (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $alloc (type 0) (param i32 i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 2 + local.get 0 + i32.store offset=12 + local.get 2 + local.get 1 + i32.store offset=8 + local.get 2 + i32.load offset=12) + (func $dealloc (type 1) (param i32) + global.get 0 + i32.const 16 + i32.sub + local.get 0 + i32.store offset=12) + (func $sym_int (type 2) (param i32) (result i32) + (local i32) + global.get 0 + i32.const 16 + i32.sub + local.tee 1 + local.get 0 + i32.store offset=12 + local.get 1 + i32.load offset=12) + (table (;0;) 5 5 funcref) + (memory (;0;) 2) + (global (;0;) (mut i32) (i32.const 66592)) + (export "memory" (memory 0)) + (export "__original_main" (func $__original_main)) + (elem (;0;) (i32.const 1) $cmp $malloc $calloc $free) + (data (;0;) (i32.const 1024) "z\00y\00x\00c\00b\00a\00") + (data (;1;) (i32.const 1036) " \04\01\00")) \ No newline at end of file From b382fe00abdc5952ae6a320a1d25eef7b5e19e13 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:06:27 -0500 Subject: [PATCH 092/105] add import --- .../pldi2026/Collection-C-normal/array/array_test_add.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_addAt2.wat | 4 ++++ .../Collection-C-normal/array/array_test_contains.wat | 4 ++++ .../Collection-C-normal/array/array_test_deepCopy.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_getAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_indexOf.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_iterAdd.wat | 4 ++++ .../Collection-C-normal/array/array_test_iterRemove.wat | 4 ++++ .../Collection-C-normal/array/array_test_iterReplace.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_reduce.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_remove.wat | 4 ++++ .../Collection-C-normal/array/array_test_removeAll.wat | 4 ++++ .../Collection-C-normal/array/array_test_removeAt.wat | 4 ++++ .../Collection-C-normal/array/array_test_replaceAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/array/array_test_reverse.wat | 4 ++++ .../Collection-C-normal/array/array_test_shallowCopy.wat | 4 ++++ .../Collection-C-normal/array/array_test_subarray.wat | 4 ++++ .../Collection-C-normal/array/array_test_zipIterAdd.wat | 4 ++++ .../Collection-C-normal/array/array_test_zipIterNext.wat | 4 ++++ .../Collection-C-normal/array/array_test_zipIterRemove.wat | 4 ++++ .../Collection-C-normal/array/array_test_zipIterReplace.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_addFirst.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_addLast.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_bufferExpansion.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_capacity.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_contains.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_copyDeep.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_copyShallow.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_filter1.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_filter2.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_filter3.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_filterMut1.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_filterMut2.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_filterMut3.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_getAt.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_getFirst.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_getLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_iterNext.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_iterRemove.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_removeAll.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_removeFirst.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_removeLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_reverse.wat | 4 ++++ .../pldi2026/Collection-C-normal/deque/deque_test_size.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_trimCapacity.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_zipIterAdd.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_zipIterNext.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_zipIterRemove.wat | 4 ++++ .../Collection-C-normal/deque/deque_test_zipIterReplace.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_add.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_addAll.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_addAllAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_addAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_addFirst.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_addLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_contains.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_copyDeep.wat | 4 ++++ .../Collection-C-normal/list/list_test_copyShallow.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_filter1.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_filter2.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_getAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_getLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_indexOf.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_iterAdd.wat | 4 ++++ .../Collection-C-normal/list/list_test_iterDescAdd.wat | 4 ++++ .../Collection-C-normal/list/list_test_iterDescRemove.wat | 4 ++++ .../Collection-C-normal/list/list_test_iterRemove.wat | 4 ++++ .../Collection-C-normal/list/list_test_mutFilter1.wat | 4 ++++ .../Collection-C-normal/list/list_test_mutFilter2.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_new.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_remove.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_removeAll.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_removeAt.wat | 4 ++++ .../Collection-C-normal/list/list_test_removeFirst.wat | 4 ++++ .../Collection-C-normal/list/list_test_removeLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_replaceAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_reverse.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_sort.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_splice.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_spliceAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_sublist.wat | 4 ++++ .../pldi2026/Collection-C-normal/list/list_test_toArray.wat | 4 ++++ .../Collection-C-normal/list/list_test_zipIterAdd.wat | 4 ++++ .../Collection-C-normal/list/list_test_zipIterNext.wat | 4 ++++ .../Collection-C-normal/list/list_test_zipIterRemove.wat | 4 ++++ .../Collection-C-normal/list/list_test_zipIterReplace.wat | 4 ++++ .../Collection-C-normal/pqueue/pqueue_test_enqueue.wat | 4 ++++ .../pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat | 4 ++++ .../pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat | 4 ++++ .../pldi2026/Collection-C-normal/queue/queue_test_iter.wat | 4 ++++ .../pldi2026/Collection-C-normal/queue/queue_test_poll.wat | 4 ++++ .../Collection-C-normal/queue/queue_test_zipIterNext.wat | 4 ++++ .../ring_buffer/ring_buffer_test_capacity.wat | 4 ++++ .../ring_buffer/ring_buffer_test_dequeue.wat | 4 ++++ .../ring_buffer/ring_buffer_test_enqueue.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_add.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_addAll.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_addAllAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_addAt.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_addFirst.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_addLast.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_contains.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_copyDeep.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_copyShallow.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_filter1.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_filter2.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_filter3.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_filterMut1.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_filterMut2.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_filterMut3.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_get.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_getFirst.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_getLast.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_iterRemove.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_new.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_remove.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_removeAll.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_removeAt.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_removeFirst.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_removeLast.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_replaceAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_reverse.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_splice.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_spliceAt.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_sublist.wat | 4 ++++ .../pldi2026/Collection-C-normal/slist/slist_test_toArray.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_zipIterAdd.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_zipIterNext.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_zipIterRemove.wat | 4 ++++ .../Collection-C-normal/slist/slist_test_zipIterReplace.wat | 4 ++++ .../pldi2026/Collection-C-normal/stack/stack_test_pop.wat | 4 ++++ .../pldi2026/Collection-C-normal/stack/stack_test_push.wat | 4 ++++ .../pldi2026/Collection-C-normal/treeset/treeset_test_add.wat | 4 ++++ .../Collection-C-normal/treeset/treeset_test_iterNext.wat | 4 ++++ .../Collection-C-normal/treeset/treeset_test_iterRemove.wat | 4 ++++ .../Collection-C-normal/treeset/treeset_test_remove.wat | 4 ++++ .../Collection-C-normal/treeset/treeset_test_removeAll.wat | 4 ++++ .../Collection-C-normal/treeset/treeset_test_size.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_add.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_get.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_getFirst.wat | 4 ++++ .../treetable/treetable_test_getGreaterThan.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_getLast.wat | 4 ++++ .../treetable/treetable_test_getLessThan.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_iterNext.wat | 4 ++++ .../treetable/treetable_test_iterRemove.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_remove.wat | 4 ++++ .../treetable/treetable_test_removeAll.wat | 4 ++++ .../treetable/treetable_test_removeFirst.wat | 4 ++++ .../treetable/treetable_test_removeLast.wat | 4 ++++ .../Collection-C-normal/treetable/treetable_test_size.wat | 4 ++++ 159 files changed, 636 insertions(+) diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat index 519d36f0a..2f2031e87 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat index 9ba6bff92..3eea3b730 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat index c7127a039..c4721287e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat index 59bbf4e82..3ffb04edc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat index 687e14125..915e1d83e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat index e0873279c..b0dcbfaee 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat index 06ae7109b..36f385209 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat index 7d8523702..d01b5461c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat index dedb8b5a6..554d07162 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat index adbaad4b3..cdd4e8e87 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat @@ -71,6 +71,10 @@ i32.load offset=12 i32.add i32.store) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat index 21ce0a636..07833adc2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat index dc5ba7e9e..87e365a85 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat index 59c0b4252..038feb79e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat index 8f6028243..09e2f2c81 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat index 1cf7dd4f9..39091e145 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat index d2d722164..ec9b6f5c0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat @@ -4,6 +4,10 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat index ce51cb260..ae903cfd7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat index 9ef31665b..22bd9a6d1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat index 3b3d0303a..ea3bd7ee6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat index 50d1f98dc..eef27f349 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32 i32))) (type (;6;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat index 210d08e0c..33a0f61af 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -7,6 +7,10 @@ (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) (type (;7;) (func (param i32 i32 i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat index e73671fbf..6d2d37051 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat index 369c1f9bc..b5d32fea9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat index c21a02130..370de1ab8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat index 4c5523bc5..66b05f7e3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat index 3950bea5d..05038cbd7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat index 99c8ffd2b..9dea2879d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat index d0c3f7560..3436c00a1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat index 29cab93d3..77198b4d8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1056 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat index af7336649..1a237082f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat index 0fbf07fe1..b811f7bc9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat index d52577f9a..755a8f977 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat @@ -16,6 +16,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat index cbf0b14a7..c3c5aadca 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat index 11459d9b7..ad862ec7e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -30,6 +30,10 @@ i32.le_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat index 59b972bad..1b6434ac5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -30,6 +30,10 @@ i32.gt_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat index 1dad6264a..54f0db64a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -30,6 +30,10 @@ i32.gt_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat index 60374b01f..762efbf31 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -30,6 +30,10 @@ i32.le_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat index 426c59ab1..7bd0e17a0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -30,6 +30,10 @@ i32.gt_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat index 4fce44482..6c4221799 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -30,6 +30,10 @@ i32.gt_s i32.const 1 i32.and) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat index 91b11eed4..88f387de0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat index b7eb36640..82519eb49 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat index 82355936f..186f1fa29 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat index 083c805dc..e65248661 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -16,6 +16,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat index b444c1e12..149c5fec9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -16,6 +16,10 @@ i32.const 0 i32.load offset=1040 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat index 67810ef64..822171adf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -16,6 +16,10 @@ i32.const 0 i32.load offset=1040 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat index ee5e4f928..072eed0af 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat index ec25a451e..4c2c13bcf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat index 0834b9f36..bc1a77dea 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat index 1a4d9e6e7..ce32fd346 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat index 5232375e6..3a9302950 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat index 8ce28f5d9..1a0c498b7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1036 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat index a1d6074c0..3f4409cc8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat index eeeeb3367..03b39170a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat index 730293d77..6fe7457ac 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -15,6 +15,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat index fe7d0fdd4..fb0d00582 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -17,6 +17,10 @@ i32.const 0 i32.load offset=1044 call $deque_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat index 1d674eb05..10b4f323e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1040 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat index b58c1873c..d99e9f6f1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat index 9636ca2da..68c8d7173 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat index c86dc5bae..0f1dd295b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1052 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat index 4e6f36e3c..601da9522 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat index 2c601e919..4216a3f31 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat index df5c0582d..920ec4824 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat index 07407781e..0f3a4f4e2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat index d33a4f7d7..7d118807a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat index 62093eb28..5d7fad989 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -198,6 +198,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat index 2559569a5..6e924f139 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -198,6 +198,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat index 9e74ccf59..57a19bbb4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat index 262be54ee..f428df95f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat index a522ab917..d3d2742dc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -19,6 +19,10 @@ i32.const 0 i32.load offset=1040 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat index ff130b855..867fce50e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1052 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat index 87fd18db7..d5cfa149c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1052 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat index 0d055954e..cb664087e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat index baa8afb12..bc55d4c76 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat index 8e02caa25..bc9ec9960 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -197,6 +197,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat index 365fc0f29..fa937e0a8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -198,6 +198,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat index 633f25c49..f8d8ed454 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1032 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat index 496d75c5b..994998cbb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat index e5c09b203..f76560cb6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat index ad97b230c..61fca2012 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat index 4433c8ba0..4bc3e0801 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat index e407ac4cf..8f86e9d41 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat index f213d98f9..e527f3870 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat @@ -184,6 +184,10 @@ i32.const 0 i32.load offset=1052 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat index 243069403..dba159b0a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat index d46ada36f..f0b663ccc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1040 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat index 77a31a8d3..e3d5b2fa5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat @@ -184,6 +184,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat index c5134ed84..1d233468a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat @@ -184,6 +184,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat index f061b522e..8e3aa644e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat @@ -184,6 +184,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat index d1221d369..99feef538 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat index f575f3877..818f9f96d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -22,6 +22,10 @@ i32.const 0 i32.load offset=1056 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat index c5d036928..b784d8a71 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat index 35906e256..4423cdb2a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1048 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat index 664d6213e..1b3af3ae0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -22,6 +22,10 @@ i32.const 0 i32.load offset=1052 call $list_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat index ab67965ad..a99712b12 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -118,6 +118,10 @@ i32.const 0 i32.load offset=1044 call $pqueue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat index 2c4969655..81e89dea2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -118,6 +118,10 @@ i32.const 0 i32.load offset=1052 call $pqueue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat index 69e0cb19a..16229f64c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1040 call $queue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat index f58d4e257..3cbb83b56 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1040 call $queue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat index 92b731f61..783e95de8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1040 call $queue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat index 7d08a848a..c0714c15d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1048 call $queue_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat index d268fa45a..a6a2dee02 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat @@ -13,6 +13,10 @@ i32.const 0 i32.load offset=1052 call $rbuf_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat index 9546a08f5..59141fd42 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat @@ -13,6 +13,10 @@ i32.const 0 i32.load offset=1048 call $rbuf_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat index a7cd653e4..406381f31 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat @@ -13,6 +13,10 @@ i32.const 0 i32.load offset=1048 call $rbuf_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat index d581d9fad..672fb876a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1040 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat index 088289953..9486c432e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat @@ -181,6 +181,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat index 2093d76d3..d099fb883 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat index f7d75781a..cede4b88f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1052 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat index e96c4e64a..81a30f3ab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat index ee801a815..198a4e2bd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat index ed1ded0d9..d6fbe8d75 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1044 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat index 27046f212..a864eb02d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat index 62a0bb54d..c85cefbe2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat index 81c50ab82..4ac378416 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -196,6 +196,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat index fa676bebb..889676109 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -197,6 +197,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat index 4b2739272..a25ecedfd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -262,6 +262,10 @@ i32.const 64 i32.add global.set 0) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 5) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat index 0c455a00a..d675b55cd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -196,6 +196,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat index 8509b81a1..ffe904785 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -197,6 +197,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat index ea4f182fc..360f79b0a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -196,6 +196,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat index cf90049a2..dd2fe0442 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat index d8d680b14..8a861f8e5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat @@ -180,6 +180,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat index 25399248b..434ac129e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat @@ -180,6 +180,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat index 3182a0c98..f8df1c770 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat @@ -19,6 +19,10 @@ i32.const 0 i32.load offset=1040 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat index d5340fdcd..8c03c9ad2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1052 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat index 3ab58e951..d5222160f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat index a50ac90e5..19c3992ab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat @@ -18,6 +18,10 @@ i32.const 0 i32.load offset=1032 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat index c4cf11f00..abfeba33d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat index 9040544e4..25f92421a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat @@ -180,6 +180,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat index 83fa2fe5c..f1c05dd5b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat index e19e4b716..2f999711b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat @@ -181,6 +181,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat index 1457b5671..8a798850d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat index e0d3f1335..cbbc5164e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1052 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat index 419b14735..72353d033 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat @@ -19,6 +19,10 @@ i32.const 0 i32.load offset=1044 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat index a6267a6a6..c39aa4088 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat index 67287f941..6cd6d4f7b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat @@ -183,6 +183,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat index 29c574b35..937636970 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat index c6f4744e4..2390d9486 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat @@ -182,6 +182,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat index 0694e8deb..a53698d9b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -20,6 +20,10 @@ i32.const 0 i32.load offset=1056 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat index 3ba3482d6..6ee6f74e4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1048 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat index c49f85c92..7892b4e5f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1052 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat index 2eb8580e1..1c5466441 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -21,6 +21,10 @@ i32.const 0 i32.load offset=1056 call $slist_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat index bc329d4ee..506a21437 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat @@ -13,6 +13,10 @@ i32.const 0 i32.load offset=1036 call $stack_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat index 48ae167a6..c5f6e6702 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat @@ -13,6 +13,10 @@ i32.const 0 i32.load offset=1036 call $stack_destroy) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat index fcba91398..fb8b61109 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat index ada499512..68c28ab04 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat index 499a94143..b91dab535 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat index 82fe3150f..c23675f31 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat index 8d4fc3dc0..f30ccd15e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat index 61eb6ff92..7610ad8b0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) (type (;5;) (func (param i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat index 9541b834b..c3276073c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat index f0093eaf7..4428f730a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat index 05ab0e1e1..879e0a6d6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat index 0683c656e..7835024aa 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat index 904724930..358c89d73 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat index 435bae4f1..a1e8c3566 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat index ad4f85eda..ca4426555 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat index cd6954924..5ce5fb331 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat index 551f338cc..20084065b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat index 7a6e19787..5db9c2f9f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat index 5b25cda87..60c7734fd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat index c043c5e18..8470701c7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -6,6 +6,10 @@ (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) (type (;6;) (func (param i32 i32 i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat index 28bf452fd..548b21f11 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -5,6 +5,10 @@ (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32))) (type (;5;) (func (param i32 i32 i32) (result i32))) + (import "i32" "symbolic" (func (;0;) (type 0))) + (import "i32" "sym_assume" (func (;1;) (type 1))) + (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 From 4f302940830a01be376d156bbe58a27cf63addaf Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:08:23 -0500 Subject: [PATCH 093/105] i32.symbolic --- .../array/array_test_add.wat | 6 ++--- .../array/array_test_addAt2.wat | 2 +- .../array/array_test_contains.wat | 8 +++---- .../array/array_test_deepCopy.wat | 6 ++--- .../array/array_test_getAt.wat | 8 +++---- .../array/array_test_indexOf.wat | 6 ++--- .../array/array_test_iterAdd.wat | 10 ++++---- .../array/array_test_iterRemove.wat | 8 +++---- .../array/array_test_iterReplace.wat | 10 ++++---- .../array/array_test_reduce.wat | 10 ++++---- .../array/array_test_remove.wat | 2 +- .../array/array_test_removeAll.wat | 2 +- .../array/array_test_removeAt.wat | 8 +++---- .../array/array_test_replaceAt.wat | 8 +++---- .../array/array_test_reverse.wat | 6 ++--- .../array/array_test_shallowCopy.wat | 6 ++--- .../array/array_test_subarray.wat | 10 ++++---- .../array/array_test_zipIterAdd.wat | 18 +++++++------- .../array/array_test_zipIterNext.wat | 14 +++++------ .../array/array_test_zipIterRemove.wat | 14 +++++------ .../array/array_test_zipIterReplace.wat | 18 +++++++------- .../deque/deque_test_addAt1.wat | 14 +++++------ .../deque/deque_test_addAt2.wat | 14 +++++------ .../deque/deque_test_addAt3.wat | 14 +++++------ .../deque/deque_test_addAt4.wat | 14 +++++------ .../deque/deque_test_addAt5.wat | 14 +++++------ .../deque/deque_test_addFirst.wat | 6 ++--- .../deque/deque_test_addLast.wat | 6 ++--- .../deque/deque_test_bufferExpansion.wat | 12 +++++----- .../deque/deque_test_capacity.wat | 6 ++--- .../deque/deque_test_contains.wat | 14 +++++------ .../deque/deque_test_copyDeep.wat | 6 ++--- .../deque/deque_test_copyShallow.wat | 6 ++--- .../deque/deque_test_filter1.wat | 12 +++++----- .../deque/deque_test_filter2.wat | 12 +++++----- .../deque/deque_test_filter3.wat | 12 +++++----- .../deque/deque_test_filterMut1.wat | 12 +++++----- .../deque/deque_test_filterMut2.wat | 12 +++++----- .../deque/deque_test_filterMut3.wat | 12 +++++----- .../deque/deque_test_getAt.wat | 6 ++--- .../deque/deque_test_getFirst.wat | 6 ++--- .../deque/deque_test_getLast.wat | 6 ++--- .../deque/deque_test_iterAdd.wat | 14 +++++------ .../deque/deque_test_iterNext.wat | 12 +++++----- .../deque/deque_test_iterRemove.wat | 12 +++++----- .../deque/deque_test_removeAll.wat | 6 ++--- .../deque/deque_test_removeFirst.wat | 8 +++---- .../deque/deque_test_removeLast.wat | 8 +++---- .../deque/deque_test_reverse.wat | 6 ++--- .../deque/deque_test_size.wat | 8 +++---- .../deque/deque_test_trimCapacity.wat | 6 ++--- .../deque/deque_test_zipIterAdd.wat | 18 +++++++------- .../deque/deque_test_zipIterNext.wat | 14 +++++------ .../deque/deque_test_zipIterRemove.wat | 14 +++++------ .../deque/deque_test_zipIterReplace.wat | 18 +++++++------- .../list/list_test_add.wat | 8 +++---- .../list/list_test_addAll.wat | 16 ++++++------- .../list/list_test_addAllAt.wat | 16 ++++++------- .../list/list_test_addAt.wat | 18 +++++++------- .../list/list_test_addFirst.wat | 10 ++++---- .../list/list_test_addLast.wat | 10 ++++---- .../list/list_test_contains.wat | 10 ++++---- .../list/list_test_copyDeep.wat | 16 ++++++------- .../list/list_test_copyShallow.wat | 16 ++++++------- .../list/list_test_filter1.wat | 16 ++++++------- .../list/list_test_filter2.wat | 16 ++++++------- .../list/list_test_getAt.wat | 16 ++++++------- .../list/list_test_getLast.wat | 16 ++++++------- .../list/list_test_indexOf.wat | 8 +++---- .../list/list_test_iterAdd.wat | 20 ++++++++-------- .../list/list_test_iterDescAdd.wat | 20 ++++++++-------- .../list/list_test_iterDescRemove.wat | 16 ++++++------- .../list/list_test_iterRemove.wat | 16 ++++++------- .../list/list_test_mutFilter1.wat | 16 ++++++------- .../list/list_test_mutFilter2.wat | 16 ++++++------- .../list/list_test_remove.wat | 16 ++++++------- .../list/list_test_removeAll.wat | 16 ++++++------- .../list/list_test_removeAt.wat | 16 ++++++------- .../list/list_test_removeFirst.wat | 16 ++++++------- .../list/list_test_removeLast.wat | 16 ++++++------- .../list/list_test_replaceAt.wat | 18 +++++++------- .../list/list_test_reverse.wat | 16 ++++++------- .../list/list_test_sort.wat | 8 +++---- .../list/list_test_splice.wat | 16 ++++++------- .../list/list_test_spliceAt.wat | 16 ++++++------- .../list/list_test_sublist.wat | 16 ++++++------- .../list/list_test_toArray.wat | 16 ++++++------- .../list/list_test_zipIterAdd.wat | 22 ++++++++--------- .../list/list_test_zipIterNext.wat | 14 +++++------ .../list/list_test_zipIterRemove.wat | 14 +++++------ .../list/list_test_zipIterReplace.wat | 18 +++++++------- .../pqueue/pqueue_test_enqueue.wat | 12 +++++----- .../pqueue/pqueue_test_pop.wat | 18 +++++++------- .../queue/queue_test_enqueue.wat | 6 ++--- .../queue/queue_test_iter.wat | 6 ++--- .../queue/queue_test_poll.wat | 6 ++--- .../queue/queue_test_zipIterNext.wat | 14 +++++------ .../ring_buffer/ring_buffer_test_capacity.wat | 24 +++++++++---------- .../ring_buffer/ring_buffer_test_dequeue.wat | 20 ++++++++-------- .../ring_buffer/ring_buffer_test_enqueue.wat | 20 ++++++++-------- .../slist/slist_test_add.wat | 8 +++---- .../slist/slist_test_addAll.wat | 16 ++++++------- .../slist/slist_test_addAllAt.wat | 16 ++++++------- .../slist/slist_test_addAt.wat | 18 +++++++------- .../slist/slist_test_addFirst.wat | 10 ++++---- .../slist/slist_test_addLast.wat | 10 ++++---- .../slist/slist_test_contains.wat | 10 ++++---- .../slist/slist_test_copyDeep.wat | 16 ++++++------- .../slist/slist_test_copyShallow.wat | 16 ++++++------- .../slist/slist_test_filter1.wat | 16 ++++++------- .../slist/slist_test_filter2.wat | 16 ++++++------- .../slist/slist_test_filter3.wat | 16 ++++++------- .../slist/slist_test_filterMut1.wat | 16 ++++++------- .../slist/slist_test_filterMut2.wat | 16 ++++++------- .../slist/slist_test_filterMut3.wat | 16 ++++++------- .../slist/slist_test_get.wat | 16 ++++++------- .../slist/slist_test_getFirst.wat | 16 ++++++------- .../slist/slist_test_getLast.wat | 16 ++++++------- .../slist/slist_test_indexOf.wat | 8 +++---- .../slist/slist_test_iterAdd.wat | 20 ++++++++-------- .../slist/slist_test_iterRemove.wat | 16 ++++++------- .../slist/slist_test_remove.wat | 16 ++++++------- .../slist/slist_test_removeAll.wat | 16 ++++++------- .../slist/slist_test_removeAt.wat | 16 ++++++------- .../slist/slist_test_removeFirst.wat | 16 ++++++------- .../slist/slist_test_removeLast.wat | 16 ++++++------- .../slist/slist_test_replaceAt.wat | 18 +++++++------- .../slist/slist_test_reverse.wat | 12 +++++----- .../slist/slist_test_splice.wat | 16 ++++++------- .../slist/slist_test_spliceAt.wat | 16 ++++++------- .../slist/slist_test_sublist.wat | 16 ++++++------- .../slist/slist_test_toArray.wat | 16 ++++++------- .../slist/slist_test_zipIterAdd.wat | 22 ++++++++--------- .../slist/slist_test_zipIterNext.wat | 14 +++++------ .../slist/slist_test_zipIterRemove.wat | 18 +++++++------- .../slist/slist_test_zipIterReplace.wat | 22 ++++++++--------- .../stack/stack_test_pop.wat | 6 ++--- .../stack/stack_test_push.wat | 6 ++--- .../treeset/treeset_test_add.wat | 6 ++--- .../treeset/treeset_test_iterNext.wat | 8 +++---- .../treeset/treeset_test_iterRemove.wat | 6 ++--- .../treeset/treeset_test_remove.wat | 6 ++--- .../treeset/treeset_test_removeAll.wat | 6 ++--- .../treeset/treeset_test_size.wat | 6 ++--- .../treetable/treetable_test_add.wat | 12 +++++----- .../treetable/treetable_test_get.wat | 10 ++++---- .../treetable/treetable_test_getFirst.wat | 16 ++++++------- .../treetable_test_getGreaterThan.wat | 16 ++++++------- .../treetable/treetable_test_getLast.wat | 16 ++++++------- .../treetable/treetable_test_getLessThan.wat | 16 ++++++------- .../treetable/treetable_test_iterNext.wat | 16 ++++++------- .../treetable/treetable_test_iterRemove.wat | 12 +++++----- .../treetable/treetable_test_remove.wat | 14 +++++------ .../treetable/treetable_test_removeAll.wat | 14 +++++------ .../treetable/treetable_test_removeFirst.wat | 16 ++++++------- .../treetable/treetable_test_removeLast.wat | 16 ++++++------- .../treetable/treetable_test_size.wat | 12 +++++----- 157 files changed, 1005 insertions(+), 1005 deletions(-) diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat index 2f2031e87..4981b1449 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat @@ -31,15 +31,15 @@ sym_assert local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat index 3eea3b730..ccc8a60c3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat @@ -23,7 +23,7 @@ drop local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 i32.const 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat index c4721287e..165ce5052 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -23,19 +23,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat index 3ffb04edc..db3364414 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat @@ -24,15 +24,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat index 915e1d83e..05b4391fc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat @@ -23,19 +23,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat index b0dcbfaee..46d5eb478 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat @@ -23,15 +23,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat index 36f385209..342e57cc0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -24,23 +24,23 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat index d01b5461c..9c4107b1a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -24,19 +24,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=28 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat index 554d07162..c008e5037 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -25,23 +25,23 @@ drop local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat index cdd4e8e87..683bd5b1c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat @@ -90,23 +90,23 @@ drop local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat index 07833adc2..ef37620ee 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -23,7 +23,7 @@ drop local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.load offset=24 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat index 87e365a85..e61f675bb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -23,7 +23,7 @@ drop local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.load offset=24 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat index 038feb79e..bcdeb4717 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat @@ -23,19 +23,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat index 09e2f2c81..0460a7c69 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat @@ -24,19 +24,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat index 39091e145..4561e64c8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat @@ -23,15 +23,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat index ec9b6f5c0..4705f11b2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat @@ -23,15 +23,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat index ae903cfd7..3b6f2cc66 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat @@ -24,23 +24,23 @@ drop local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=24 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat index 22bd9a6d1..9c086f0dd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -24,7 +24,7 @@ drop local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=104 local.get 0 local.get 0 @@ -35,7 +35,7 @@ i32.store8 offset=103 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=96 local.get 0 local.get 0 @@ -46,7 +46,7 @@ i32.store8 offset=95 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -57,7 +57,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -68,7 +68,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -79,7 +79,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -90,7 +90,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -101,7 +101,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 @@ -112,7 +112,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat index ea3bd7ee6..54a1d66b4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat @@ -25,7 +25,7 @@ drop local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -36,7 +36,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -47,7 +47,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -58,7 +58,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -69,7 +69,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -80,7 +80,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 @@ -91,7 +91,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat index eef27f349..8bfd2d771 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -25,7 +25,7 @@ drop local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -36,7 +36,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -47,7 +47,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -58,7 +58,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -69,7 +69,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -80,7 +80,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 @@ -91,7 +91,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat index 33a0f61af..407a86afe 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -26,7 +26,7 @@ drop local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=120 local.get 0 local.get 0 @@ -37,7 +37,7 @@ i32.store8 offset=119 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=112 local.get 0 local.get 0 @@ -48,7 +48,7 @@ i32.store8 offset=111 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 local.get 0 @@ -59,7 +59,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 local.get 0 @@ -70,7 +70,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -81,7 +81,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -92,7 +92,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -103,7 +103,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -114,7 +114,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat index 6d2d37051..cca168a1d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat index b5d32fea9..31374b79a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat index 370de1ab8..e502d1dbc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat index 66b05f7e3..e20b84f64 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat index 05038cbd7..a759652d9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat index 9dea2879d..1ca6a09f4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat index 3436c00a1..509c4b5b3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat index 77198b4d8..4c5f91305 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat @@ -37,27 +37,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=36 i32.const 0 i32.load offset=1056 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat index 1a237082f..d0aada4da 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat @@ -55,15 +55,15 @@ sym_assert local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.load offset=20 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat index b811f7bc9..c485cf4d4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat @@ -32,31 +32,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat index 755a8f977..3deef1f09 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat @@ -45,15 +45,15 @@ i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.load offset=40 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat index c3c5aadca..dbeba7b03 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat index ad862ec7e..97c85acc4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat index 1b6434ac5..5208e18a6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat index 54f0db64a..c643f1641 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat index 762efbf31..424234fc2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=4 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat index 7bd0e17a0..fd51c0cd6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=4 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat index 6c4221799..a779f6365 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -47,27 +47,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=4 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat index 88f387de0..d16a92133 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat index 82519eb49..df59c5d70 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat index 186f1fa29..e7697d256 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat index e65248661..cbab6d6b9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -33,31 +33,31 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat index 149c5fec9..d1f05f703 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -33,27 +33,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=36 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat index 822171adf..3d32181be 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -33,27 +33,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat index 072eed0af..913d7f550 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat index 4c2c13bcf..7be1f58e0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat @@ -32,19 +32,19 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat index bc1a77dea..0d31c2fe9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat @@ -32,19 +32,19 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat index ce32fd346..cc7abc33a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat index 3a9302950..451737f3e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat @@ -32,19 +32,19 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat index 1a0c498b7..01588bdcc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat @@ -32,15 +32,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat index 3f4409cc8..056379bfc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -32,7 +32,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -57,7 +57,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -82,7 +82,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -107,7 +107,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -132,7 +132,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -157,7 +157,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -182,7 +182,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 @@ -295,7 +295,7 @@ drop local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 @@ -306,7 +306,7 @@ i32.store8 offset=43 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=36 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat index 03b39170a..f4b65a70b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -32,7 +32,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -43,7 +43,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -54,7 +54,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -65,7 +65,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -76,7 +76,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -87,7 +87,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 @@ -98,7 +98,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat index 6fe7457ac..093f85b09 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -32,7 +32,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -57,7 +57,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -82,7 +82,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -107,7 +107,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -132,7 +132,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 @@ -157,7 +157,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.load offset=48 @@ -182,7 +182,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.load offset=40 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat index fb0d00582..79ace7833 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -34,7 +34,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -59,7 +59,7 @@ i32.store8 offset=119 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -84,7 +84,7 @@ i32.store8 offset=111 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -109,7 +109,7 @@ i32.store8 offset=103 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -134,7 +134,7 @@ i32.store8 offset=95 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -159,7 +159,7 @@ i32.store8 offset=87 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -184,7 +184,7 @@ i32.store8 offset=79 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -297,7 +297,7 @@ drop local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=60 local.get 0 local.get 0 @@ -308,7 +308,7 @@ i32.store8 offset=59 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=52 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat index 10b4f323e..9cbdb4f03 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat @@ -32,7 +32,7 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 @@ -43,7 +43,7 @@ i32.store8 offset=43 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 local.get 0 @@ -54,7 +54,7 @@ i32.store8 offset=35 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -65,7 +65,7 @@ i32.store8 offset=27 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat index d99e9f6f1..3dae8062e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat index 68c8d7173..7d72682f0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat index 0f1dd295b..c2ec2ff3d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -197,7 +197,7 @@ call $setup_tests local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat index 601da9522..a09cea0ff 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat @@ -32,23 +32,23 @@ call $setup_tests local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat index 4216a3f31..476c523c5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat @@ -32,23 +32,23 @@ call $setup_tests local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat index 920ec4824..898d6b48b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -35,23 +35,23 @@ call $setup_tests local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat index 0f3a4f4e2..d63bc10d3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat index 7d118807a..927c16b60 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat index 5d7fad989..273d2027a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -36,35 +36,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat index 6e924f139..19902d85e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -36,35 +36,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat index 57a19bbb4..fcb5f0af5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat index f428df95f..0ddb7e546 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat index d3d2742dc..7cfd48ef4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -36,19 +36,19 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat index 867fce50e..4cee093c5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -200,7 +200,7 @@ call $setup_tests local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 4 @@ -369,7 +369,7 @@ call $list_iter_init local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat index d5cfa149c..99f896833 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -208,11 +208,11 @@ i32.store offset=36 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.load offset=40 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat index cb664087e..646d6397f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat index bc55d4c76..d4a0aaedc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat index bc9ec9960..d47142739 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -35,35 +35,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat index fa937e0a8..da7e0fdba 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -36,35 +36,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat index 994998cbb..b487be24e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat index f76560cb6..289e6a494 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat index 61fca2012..77a9d8e95 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat index 4bc3e0801..3aad1f1ff 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat index 8f86e9d41..3385ce685 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat index e527f3870..8bf7c52ae 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -198,7 +198,7 @@ call $setup_tests local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat index dba159b0a..4e51b41f3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat index f0b663ccc..64eb5eb7d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat @@ -37,19 +37,19 @@ call $setup_tests local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=28 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat index e3d5b2fa5..75f04e77a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat index 1d233468a..0b49e62f4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat index 8e3aa644e..8bdc587c2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat index 99feef538..38d7620b0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat index 818f9f96d..1ebd0ac0c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -39,7 +39,7 @@ call $setup_tests local.get 0 i32.const 1044 - i32.symbolic + call 0 i32.store offset=136 local.get 0 i32.load offset=136 @@ -64,7 +64,7 @@ i32.store8 offset=135 local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=128 local.get 0 i32.load offset=128 @@ -89,7 +89,7 @@ i32.store8 offset=127 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -114,7 +114,7 @@ i32.store8 offset=119 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -139,7 +139,7 @@ i32.store8 offset=111 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -164,7 +164,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -189,7 +189,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -214,7 +214,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -239,7 +239,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -264,7 +264,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -289,7 +289,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat index b784d8a71..145897352 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat @@ -38,7 +38,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 local.get 0 @@ -49,7 +49,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 local.get 0 @@ -60,7 +60,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -71,7 +71,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -82,7 +82,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -93,7 +93,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -104,7 +104,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat index 4423cdb2a..88c114bd6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -38,7 +38,7 @@ call $setup_tests local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -63,7 +63,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -88,7 +88,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -113,7 +113,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -138,7 +138,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -163,7 +163,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -188,7 +188,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat index 1b3af3ae0..8ab1ae0c8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -39,7 +39,7 @@ call $setup_tests local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -64,7 +64,7 @@ i32.store8 offset=119 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -89,7 +89,7 @@ i32.store8 offset=111 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -114,7 +114,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -139,7 +139,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -164,7 +164,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -189,7 +189,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -214,7 +214,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -239,7 +239,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat index a99712b12..28ccbd5e9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -135,27 +135,27 @@ call $setup_tests local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat index 81e89dea2..77b902db9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -135,39 +135,39 @@ call $setup_tests local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat index 16229f64c..8c00a011e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat @@ -37,15 +37,15 @@ call $setup_test local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat index 3cbb83b56..0fe59babc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat @@ -38,15 +38,15 @@ call $setup_test local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat index 783e95de8..51f2840b9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat @@ -37,15 +37,15 @@ call $setup_test local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat index c0714c15d..ba3a6c78f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat @@ -37,7 +37,7 @@ call $setup_test local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=88 local.get 0 local.get 0 @@ -48,7 +48,7 @@ i32.store8 offset=87 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=80 local.get 0 local.get 0 @@ -59,7 +59,7 @@ i32.store8 offset=79 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -70,7 +70,7 @@ i32.store8 offset=71 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -81,7 +81,7 @@ i32.store8 offset=63 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -92,7 +92,7 @@ i32.store8 offset=55 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 @@ -103,7 +103,7 @@ i32.store8 offset=47 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat index a6a2dee02..8a71dec20 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat @@ -30,7 +30,7 @@ call $setup_test local.get 0 i32.const 1046 - i32.symbolic + call 0 i32.store offset=108 local.get 0 local.get 0 @@ -41,7 +41,7 @@ i32.store8 offset=107 local.get 0 i32.const 1044 - i32.symbolic + call 0 i32.store offset=100 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=99 local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=92 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=91 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=84 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=83 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=76 local.get 0 local.get 0 @@ -85,7 +85,7 @@ i32.store8 offset=75 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=68 local.get 0 local.get 0 @@ -96,7 +96,7 @@ i32.store8 offset=67 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=60 local.get 0 local.get 0 @@ -107,7 +107,7 @@ i32.store8 offset=59 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 local.get 0 @@ -118,7 +118,7 @@ i32.store8 offset=51 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 @@ -129,7 +129,7 @@ i32.store8 offset=43 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 local.get 0 @@ -276,7 +276,7 @@ sym_assert local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -287,7 +287,7 @@ i32.store8 offset=27 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat index 59141fd42..b2553eca7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat @@ -30,7 +30,7 @@ call $setup_test local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=92 local.get 0 local.get 0 @@ -41,7 +41,7 @@ i32.store8 offset=91 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=84 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=83 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=76 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=75 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=68 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=67 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=60 local.get 0 local.get 0 @@ -85,7 +85,7 @@ i32.store8 offset=59 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 local.get 0 @@ -96,7 +96,7 @@ i32.store8 offset=51 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 @@ -107,7 +107,7 @@ i32.store8 offset=43 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 local.get 0 @@ -118,7 +118,7 @@ i32.store8 offset=35 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -129,7 +129,7 @@ i32.store8 offset=27 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat index 406381f31..c14de4088 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat @@ -30,7 +30,7 @@ call $setup_test local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=92 local.get 0 local.get 0 @@ -41,7 +41,7 @@ i32.store8 offset=91 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=84 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=83 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=76 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=75 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=68 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=67 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=60 local.get 0 local.get 0 @@ -85,7 +85,7 @@ i32.store8 offset=59 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 local.get 0 @@ -96,7 +96,7 @@ i32.store8 offset=51 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 @@ -107,7 +107,7 @@ i32.store8 offset=43 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=36 local.get 0 local.get 0 @@ -118,7 +118,7 @@ i32.store8 offset=35 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -129,7 +129,7 @@ i32.store8 offset=27 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat index 672fb876a..1a08b8f91 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat @@ -35,7 +35,7 @@ call $setup_test local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -46,7 +46,7 @@ i32.store8 offset=39 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -57,7 +57,7 @@ i32.store8 offset=31 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -68,7 +68,7 @@ i32.store8 offset=23 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat index 9486c432e..781137aeb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat index d099fb883..e0773d460 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat index cede4b88f..a60306c8e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -199,7 +199,7 @@ call $setup_test local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat index 81a30f3ab..15731525b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat @@ -35,23 +35,23 @@ call $setup_test local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat index 198a4e2bd..eccbc2628 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat @@ -35,23 +35,23 @@ call $setup_test local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat index d6fbe8d75..7fbcadf5b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat @@ -35,23 +35,23 @@ call $setup_test local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=12 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat index a864eb02d..82ec4a2d2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat index c85cefbe2..9c9c163c4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat index 4ac378416..e3997b813 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -35,35 +35,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat index 889676109..df61d6ec6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -36,35 +36,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat index a25ecedfd..1bb06ff92 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -37,35 +37,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat index d675b55cd..122227c4d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -35,35 +35,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat index ffe904785..8dcf68605 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -36,35 +36,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat index 360f79b0a..2fdde218f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -35,35 +35,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat index dd2fe0442..4f2b6724f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat index 8a861f8e5..769bbb924 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat @@ -19,35 +19,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat index 434ac129e..c64f55d70 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat @@ -19,35 +19,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat index f8df1c770..674b3ad95 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat @@ -36,19 +36,19 @@ call $setup_test local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=12 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat index 8c03c9ad2..e421e735d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -200,7 +200,7 @@ call $setup_test local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 4 @@ -365,7 +365,7 @@ sym_assert local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat index d5222160f..113fc517c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat index abfeba33d..85be2cf02 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat index 25f92421a..73ae3e524 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat @@ -19,35 +19,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat index f1c05dd5b..02b74f15a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat index 2f999711b..de7db3992 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat @@ -20,35 +20,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat index 8a798850d..bc6f20c12 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat index cbbc5164e..1eec1ffec 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1080 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1084 local.get 0 i32.const 4 @@ -199,7 +199,7 @@ call $setup_test local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat index 72353d033..fb76a5db1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat @@ -36,27 +36,27 @@ call $setup_test local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=84 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=76 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=68 i32.const 0 i32.load offset=1040 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat index c39aa4088..c560c3c44 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat index 6cd6d4f7b..6988899c9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat @@ -22,35 +22,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat index 937636970..a1084f79b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat index 2390d9486..2fdf3a436 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat @@ -21,35 +21,35 @@ drop i32.const 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=1052 i32.const 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=1056 i32.const 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=1060 i32.const 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=1064 i32.const 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=1068 i32.const 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=1072 i32.const 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=1076 i32.const 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=1080 local.get 0 i32.const 4 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat index a53698d9b..f9bca7320 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -37,7 +37,7 @@ call $setup_test local.get 0 i32.const 1044 - i32.symbolic + call 0 i32.store offset=136 local.get 0 i32.load offset=136 @@ -62,7 +62,7 @@ i32.store8 offset=135 local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=128 local.get 0 i32.load offset=128 @@ -87,7 +87,7 @@ i32.store8 offset=127 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -112,7 +112,7 @@ i32.store8 offset=119 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -137,7 +137,7 @@ i32.store8 offset=111 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -162,7 +162,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -187,7 +187,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -212,7 +212,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -237,7 +237,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -262,7 +262,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -287,7 +287,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat index 6ee6f74e4..201d82b71 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -38,7 +38,7 @@ call $setup_test local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -63,7 +63,7 @@ i32.store8 offset=103 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -88,7 +88,7 @@ i32.store8 offset=95 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -113,7 +113,7 @@ i32.store8 offset=87 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -138,7 +138,7 @@ i32.store8 offset=79 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 @@ -163,7 +163,7 @@ i32.store8 offset=71 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=64 local.get 0 i32.load offset=64 @@ -188,7 +188,7 @@ i32.store8 offset=63 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat index 7892b4e5f..974193eb7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -38,7 +38,7 @@ call $setup_test local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=136 local.get 0 i32.load offset=136 @@ -63,7 +63,7 @@ i32.store8 offset=135 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=128 local.get 0 i32.load offset=128 @@ -88,7 +88,7 @@ i32.store8 offset=127 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -113,7 +113,7 @@ i32.store8 offset=119 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -138,7 +138,7 @@ i32.store8 offset=111 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -163,7 +163,7 @@ i32.store8 offset=103 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -188,7 +188,7 @@ i32.store8 offset=95 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -213,7 +213,7 @@ i32.store8 offset=87 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -238,7 +238,7 @@ i32.store8 offset=79 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat index 1c5466441..260b0e370 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -38,7 +38,7 @@ call $setup_test local.get 0 i32.const 1044 - i32.symbolic + call 0 i32.store offset=152 local.get 0 i32.load offset=152 @@ -63,7 +63,7 @@ i32.store8 offset=151 local.get 0 i32.const 1042 - i32.symbolic + call 0 i32.store offset=144 local.get 0 i32.load offset=144 @@ -88,7 +88,7 @@ i32.store8 offset=143 local.get 0 i32.const 1040 - i32.symbolic + call 0 i32.store offset=136 local.get 0 i32.load offset=136 @@ -113,7 +113,7 @@ i32.store8 offset=135 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=128 local.get 0 i32.load offset=128 @@ -138,7 +138,7 @@ i32.store8 offset=127 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=120 local.get 0 i32.load offset=120 @@ -163,7 +163,7 @@ i32.store8 offset=119 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=112 local.get 0 i32.load offset=112 @@ -188,7 +188,7 @@ i32.store8 offset=111 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=104 local.get 0 i32.load offset=104 @@ -213,7 +213,7 @@ i32.store8 offset=103 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=96 local.get 0 i32.load offset=96 @@ -238,7 +238,7 @@ i32.store8 offset=95 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.load offset=88 @@ -263,7 +263,7 @@ i32.store8 offset=87 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.load offset=80 @@ -288,7 +288,7 @@ i32.store8 offset=79 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.load offset=72 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat index 506a21437..b51ac5196 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat @@ -30,15 +30,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat index c5f6e6702..3fcbfc0e9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat @@ -30,15 +30,15 @@ call $setup_tests local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=24 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=20 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=16 i32.const 0 i32.load offset=1036 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat index fb8b61109..028b1e77e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -25,15 +25,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat index 68c28ab04..84c6faf0c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -25,19 +25,19 @@ drop local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=44 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat index b91dab535..00d8af1bf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -26,15 +26,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat index c23675f31..ff56326d4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -26,15 +26,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat index f30ccd15e..170692609 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -25,15 +25,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat index 7610ad8b0..c9eaa17f2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -25,15 +25,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=8 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=4 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store i32.const 0 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat index c3276073c..70d43a8c7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -22,19 +22,19 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -45,7 +45,7 @@ i32.store8 offset=31 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -56,7 +56,7 @@ i32.store8 offset=23 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat index 4428f730a..685674247 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -22,19 +22,19 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -45,7 +45,7 @@ i32.store8 offset=31 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat index 879e0a6d6..87252e455 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -25,23 +25,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat index 7835024aa..010226464 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -25,23 +25,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat index 358c89d73..12c5f656f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -25,23 +25,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat index a1e8c3566..f32285727 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -25,23 +25,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -52,7 +52,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -63,7 +63,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -74,7 +74,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat index ca4426555..8f22805f4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -25,19 +25,19 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=88 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=84 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=80 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=76 i32.const 0 local.set 1 @@ -75,7 +75,7 @@ sym_assume local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=72 local.get 0 local.get 0 @@ -86,7 +86,7 @@ i32.store8 offset=71 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=64 local.get 0 local.get 0 @@ -97,7 +97,7 @@ i32.store8 offset=63 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=56 local.get 0 local.get 0 @@ -108,7 +108,7 @@ i32.store8 offset=55 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=48 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat index 5ce5fb331..3f4a37f46 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -26,15 +26,15 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=72 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=68 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=64 i32.const 0 local.set 1 @@ -61,7 +61,7 @@ sym_assume local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=60 local.get 0 local.get 0 @@ -72,7 +72,7 @@ i32.store8 offset=59 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=52 local.get 0 local.get 0 @@ -83,7 +83,7 @@ i32.store8 offset=51 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat index 20084065b..9024f48fb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -26,23 +26,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=28 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -53,7 +53,7 @@ i32.store8 offset=23 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 @@ -64,7 +64,7 @@ i32.store8 offset=15 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=8 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat index 5db9c2f9f..96f73c29d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat @@ -22,23 +22,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -49,7 +49,7 @@ i32.store8 offset=27 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 @@ -60,7 +60,7 @@ i32.store8 offset=19 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=12 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat index 60c7734fd..3d005d74f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -26,23 +26,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -53,7 +53,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -64,7 +64,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -75,7 +75,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat index 8470701c7..c65ad3544 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -26,23 +26,23 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=56 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=52 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=48 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=44 local.get 0 i32.const 1038 - i32.symbolic + call 0 i32.store offset=40 local.get 0 local.get 0 @@ -53,7 +53,7 @@ i32.store8 offset=39 local.get 0 i32.const 1036 - i32.symbolic + call 0 i32.store offset=32 local.get 0 local.get 0 @@ -64,7 +64,7 @@ i32.store8 offset=31 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=24 local.get 0 local.get 0 @@ -75,7 +75,7 @@ i32.store8 offset=23 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=16 local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat index 548b21f11..d81414a56 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -25,19 +25,19 @@ drop local.get 0 i32.const 1028 - i32.symbolic + call 0 i32.store offset=40 local.get 0 i32.const 1026 - i32.symbolic + call 0 i32.store offset=36 local.get 0 i32.const 1024 - i32.symbolic + call 0 i32.store offset=32 local.get 0 i32.const 1034 - i32.symbolic + call 0 i32.store offset=28 local.get 0 local.get 0 @@ -48,7 +48,7 @@ i32.store8 offset=27 local.get 0 i32.const 1032 - i32.symbolic + call 0 i32.store offset=20 local.get 0 local.get 0 @@ -59,7 +59,7 @@ i32.store8 offset=19 local.get 0 i32.const 1030 - i32.symbolic + call 0 i32.store offset=12 local.get 0 local.get 0 From fb61bfbd0ed230044f515947c4dbf556c016ec0e Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:10:22 -0500 Subject: [PATCH 094/105] sym_assume is call 1 --- .../array/array_test_contains.wat | 2 +- .../array/array_test_iterAdd.wat | 2 +- .../array/array_test_iterRemove.wat | 2 +- .../array/array_test_iterReplace.wat | 2 +- .../array/array_test_remove.wat | 4 +- .../array/array_test_removeAll.wat | 4 +- .../array/array_test_zipIterAdd.wat | 2 +- .../array/array_test_zipIterRemove.wat | 2 +- .../array/array_test_zipIterReplace.wat | 2 +- .../deque/deque_test_filter1.wat | 2 +- .../deque/deque_test_filter2.wat | 2 +- .../deque/deque_test_filter3.wat | 2 +- .../deque/deque_test_filterMut1.wat | 2 +- .../deque/deque_test_filterMut2.wat | 2 +- .../deque/deque_test_filterMut3.wat | 2 +- .../deque/deque_test_iterAdd.wat | 2 +- .../deque/deque_test_iterNext.wat | 2 +- .../deque/deque_test_iterRemove.wat | 2 +- .../deque/deque_test_zipIterAdd.wat | 30 +++++------ .../deque/deque_test_zipIterNext.wat | 2 +- .../deque/deque_test_zipIterRemove.wat | 30 +++++------ .../deque/deque_test_zipIterReplace.wat | 30 +++++------ .../list/list_test_contains.wat | 2 +- .../list/list_test_filter1.wat | 2 +- .../list/list_test_filter2.wat | 2 +- .../list/list_test_indexOf.wat | 2 +- .../list/list_test_iterAdd.wat | 4 +- .../list/list_test_iterDescAdd.wat | 2 +- .../list/list_test_iterDescRemove.wat | 2 +- .../list/list_test_iterRemove.wat | 2 +- .../list/list_test_mutFilter1.wat | 2 +- .../list/list_test_mutFilter2.wat | 2 +- .../list/list_test_remove.wat | 2 +- .../list/list_test_zipIterAdd.wat | 54 +++++++++---------- .../list/list_test_zipIterRemove.wat | 30 +++++------ .../list/list_test_zipIterReplace.wat | 40 +++++++------- .../pqueue/pqueue_test_enqueue.wat | 12 ++--- .../pqueue/pqueue_test_pop.wat | 10 ++-- .../slist/slist_test_filter1.wat | 2 +- .../slist/slist_test_filter2.wat | 2 +- .../slist/slist_test_filter3.wat | 2 +- .../slist/slist_test_filterMut1.wat | 2 +- .../slist/slist_test_filterMut2.wat | 2 +- .../slist/slist_test_filterMut3.wat | 2 +- .../slist/slist_test_iterAdd.wat | 2 +- .../slist/slist_test_iterRemove.wat | 2 +- .../slist/slist_test_remove.wat | 2 +- .../slist/slist_test_zipIterAdd.wat | 52 +++++++++--------- .../slist/slist_test_zipIterNext.wat | 28 +++++----- .../slist/slist_test_zipIterRemove.wat | 42 +++++++-------- .../slist/slist_test_zipIterReplace.wat | 50 ++++++++--------- .../treeset/treeset_test_add.wat | 2 +- .../treeset/treeset_test_iterNext.wat | 2 +- .../treeset/treeset_test_iterRemove.wat | 2 +- .../treeset/treeset_test_remove.wat | 2 +- .../treeset/treeset_test_removeAll.wat | 2 +- .../treeset/treeset_test_size.wat | 2 +- .../treetable/treetable_test_add.wat | 4 +- .../treetable/treetable_test_get.wat | 2 +- .../treetable/treetable_test_getFirst.wat | 2 +- .../treetable_test_getGreaterThan.wat | 2 +- .../treetable/treetable_test_getLast.wat | 2 +- .../treetable/treetable_test_getLessThan.wat | 2 +- .../treetable/treetable_test_iterNext.wat | 2 +- .../treetable/treetable_test_iterRemove.wat | 2 +- .../treetable/treetable_test_remove.wat | 2 +- .../treetable/treetable_test_removeFirst.wat | 2 +- .../treetable/treetable_test_removeLast.wat | 2 +- .../treetable/treetable_test_size.wat | 2 +- 69 files changed, 265 insertions(+), 265 deletions(-) diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat index 165ce5052..0e592040d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -103,7 +103,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat index 342e57cc0..236775f11 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -86,7 +86,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat index 9c4107b1a..5466fc79c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -99,7 +99,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat index c008e5037..9ef16ea31 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -87,7 +87,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat index ef37620ee..6fb4929b0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -31,14 +31,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=24 i32.const 16 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat index e61f675bb..f7298a50a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -31,14 +31,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=24 i32.const 16 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat index 9c086f0dd..c26423cb3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -259,7 +259,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat index 8bfd2d771..e1ce4f68e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -139,7 +139,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat index 407a86afe..c87cc583d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -261,7 +261,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat index 97c85acc4..b13e484b2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -118,7 +118,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat index 5208e18a6..3fe5cbf3c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -121,7 +121,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat index c643f1641..e7a68b956 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -119,7 +119,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat index 424234fc2..8143e6167 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -118,7 +118,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat index fd51c0cd6..c1a1829dc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -121,7 +121,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat index a779f6365..178c32d61 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -119,7 +119,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat index cbab6d6b9..956d10442 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -156,7 +156,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat index d1f05f703..97d65dfe6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -152,7 +152,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 24 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat index 3d32181be..f2f77ccf0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -152,7 +152,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 8 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat index 056379bfc..a7cfa451a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -40,14 +40,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -65,14 +65,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -90,14 +90,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -115,14 +115,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -140,14 +140,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -165,14 +165,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -190,14 +190,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -238,7 +238,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat index f4b65a70b..67f1ecf6e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -140,7 +140,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat index 093f85b09..707d7cbac 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -40,14 +40,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -65,14 +65,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -90,14 +90,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -115,14 +115,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -140,14 +140,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -165,14 +165,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=48 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=48 @@ -190,14 +190,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=40 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=40 @@ -238,7 +238,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat index 79ace7833..7fd25c05c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -42,14 +42,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -67,14 +67,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -92,14 +92,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -117,14 +117,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -142,14 +142,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -167,14 +167,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -192,14 +192,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -240,7 +240,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat index 898d6b48b..05ffef0f5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -163,7 +163,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat index 273d2027a..cd759be1b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -241,7 +241,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=8 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat index 19902d85e..0c9228bfd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -253,7 +253,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=8 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat index 7cfd48ef4..4d8241bb6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -116,7 +116,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat index 4cee093c5..3524f9b02 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -218,7 +218,7 @@ i32.ne i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 32 i32.add @@ -280,7 +280,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 block ;; label = @1 loop ;; label = @2 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat index 99f896833..6f9a628d5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -279,7 +279,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 8 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat index 646d6397f..be73df67a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -259,7 +259,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 block ;; label = @1 loop ;; label = @2 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat index d4a0aaedc..f665a9109 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -231,7 +231,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 i32.const 2 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat index d47142739..9051ef42d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -240,7 +240,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 4 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat index da7e0fdba..cfc3368f6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -253,7 +253,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 4 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat index b487be24e..03cff88ba 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -231,7 +231,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 i32.const 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat index 1ebd0ac0c..dbfab160e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -47,14 +47,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=136 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=136 @@ -72,14 +72,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=128 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=128 @@ -97,14 +97,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -122,14 +122,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -147,14 +147,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -172,14 +172,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -197,14 +197,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -222,14 +222,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -247,14 +247,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -272,14 +272,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -297,14 +297,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -367,7 +367,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -412,7 +412,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -446,7 +446,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -480,7 +480,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -591,7 +591,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1052 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat index 88c114bd6..f4468b4ce 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -46,14 +46,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -71,14 +71,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -96,14 +96,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -121,14 +121,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -146,14 +146,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -171,14 +171,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -196,14 +196,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -442,7 +442,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat index 8ab1ae0c8..c94b23b64 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -47,14 +47,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -72,14 +72,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -97,14 +97,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -122,14 +122,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -147,14 +147,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -172,14 +172,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -197,14 +197,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -222,14 +222,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -247,14 +247,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -372,7 +372,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -439,7 +439,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat index 28ccbd5e9..a57ff9712 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -177,7 +177,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -198,7 +198,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 @@ -304,7 +304,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -325,7 +325,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -346,7 +346,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -367,7 +367,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.get 0 i32.load offset=40 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat index 77b902db9..3645d7dd5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -189,7 +189,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -210,7 +210,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -231,7 +231,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -254,7 +254,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 @@ -370,7 +370,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1052 i32.const 1056 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat index e3997b813..b21ab3e7f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -239,7 +239,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=8 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat index df61d6ec6..836728e6a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -238,7 +238,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=40 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat index 1bb06ff92..d0108a608 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -305,7 +305,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 0 i32.store offset=8 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat index 122227c4d..72615c060 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -239,7 +239,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 4 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat index 8dcf68605..857302bda 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -238,7 +238,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 4 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat index 2fdde218f..b4a5e599a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -239,7 +239,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 4 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat index e421e735d..d69fdadc8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -283,7 +283,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 block ;; label = @1 loop ;; label = @2 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat index 113fc517c..9f0b74e87 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -231,7 +231,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 i32.const 2 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat index 85be2cf02..784486903 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -230,7 +230,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.const 0 i32.load offset=1044 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat index f9bca7320..4b52e9943 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -45,14 +45,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=136 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=136 @@ -70,14 +70,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=128 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=128 @@ -95,14 +95,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -120,14 +120,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -145,14 +145,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -170,14 +170,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -195,14 +195,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -220,14 +220,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -245,14 +245,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -270,14 +270,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -295,14 +295,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 @@ -343,7 +343,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -388,7 +388,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -411,7 +411,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -445,7 +445,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1052 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat index 201d82b71..c64adff86 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -46,14 +46,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -71,14 +71,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -96,14 +96,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -121,14 +121,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -146,14 +146,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -171,14 +171,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=64 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=64 @@ -196,14 +196,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=56 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=56 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat index 974193eb7..bbb5b52d7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -46,14 +46,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=136 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=136 @@ -71,14 +71,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=128 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=128 @@ -96,14 +96,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -121,14 +121,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -146,14 +146,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -171,14 +171,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -196,14 +196,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -221,14 +221,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -246,14 +246,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -294,7 +294,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -317,7 +317,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 local.get 0 @@ -325,7 +325,7 @@ i32.ne i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1048 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat index 260b0e370..3513e47a6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -46,14 +46,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=152 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=152 @@ -71,14 +71,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=144 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=144 @@ -96,14 +96,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=136 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=136 @@ -121,14 +121,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=128 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=128 @@ -146,14 +146,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=120 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=120 @@ -171,14 +171,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=112 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=112 @@ -196,14 +196,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=104 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=104 @@ -221,14 +221,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=96 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=96 @@ -246,14 +246,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=88 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=88 @@ -271,14 +271,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=80 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=80 @@ -296,14 +296,14 @@ i32.gt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=72 i32.const 127 i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 local.get 0 i32.load offset=72 @@ -344,7 +344,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -389,7 +389,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 local.set 1 block ;; label = @1 @@ -423,7 +423,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1052 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat index 028b1e77e..f1cdaa861 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -68,7 +68,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat index 84c6faf0c..b5f4c7bab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -72,7 +72,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat index 00d8af1bf..7d78687f8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -69,7 +69,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat index ff56326d4..bcdf07641 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -69,7 +69,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat index 170692609..1ff68a514 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -68,7 +68,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat index c9eaa17f2..187c62750 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -68,7 +68,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1036 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat index 70d43a8c7..3b061b209 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -72,7 +72,7 @@ i32.lt_s i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.load offset=24 local.get 0 @@ -80,7 +80,7 @@ i32.lt_s i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat index 685674247..f1615b826 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -61,7 +61,7 @@ i32.ne i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat index 87252e455..6c577bf49 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -116,7 +116,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat index 010226464..a32b702ba 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -116,7 +116,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat index 12c5f656f..17fbcfb43 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -116,7 +116,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat index f32285727..dc661735d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -116,7 +116,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat index 8f22805f4..b56cd145a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -72,7 +72,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 1038 call 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat index 3f4a37f46..1aaf3ec81 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -58,7 +58,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 local.get 0 i32.const 1034 call 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat index 9024f48fb..90318582c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -95,7 +95,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat index 3d005d74f..acf46d15c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -117,7 +117,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat index c65ad3544..9c631efcc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -117,7 +117,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat index d81414a56..316ff4e65 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -101,7 +101,7 @@ local.get 1 i32.const 1 i32.and - sym_assume + call 1 i32.const 0 i32.load offset=1040 local.get 0 From c5a1392e46f41b5f715491ddbed3fbc62d274b6c Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:11:17 -0500 Subject: [PATCH 095/105] sym_assert is call 2 --- .../array/array_test_add.wat | 8 +++---- .../array/array_test_addAt2.wat | 4 ++-- .../array/array_test_contains.wat | 6 ++--- .../array/array_test_deepCopy.wat | 4 ++-- .../array/array_test_getAt.wat | 4 ++-- .../array/array_test_indexOf.wat | 4 ++-- .../array/array_test_iterAdd.wat | 8 +++---- .../array/array_test_iterRemove.wat | 2 +- .../array/array_test_iterReplace.wat | 4 ++-- .../array/array_test_reduce.wat | 6 ++--- .../array/array_test_remove.wat | 2 +- .../array/array_test_removeAll.wat | 2 +- .../array/array_test_removeAt.wat | 4 ++-- .../array/array_test_replaceAt.wat | 4 ++-- .../array/array_test_reverse.wat | 6 ++--- .../array/array_test_shallowCopy.wat | 4 ++-- .../array/array_test_subarray.wat | 8 +++---- .../array/array_test_zipIterAdd.wat | 20 ++++++++--------- .../array/array_test_zipIterNext.wat | 4 ++-- .../array/array_test_zipIterRemove.wat | 10 ++++----- .../array/array_test_zipIterReplace.wat | 12 +++++----- .../deque/deque_test_addAt1.wat | 6 ++--- .../deque/deque_test_addAt2.wat | 8 +++---- .../deque/deque_test_addAt3.wat | 8 +++---- .../deque/deque_test_addAt4.wat | 8 +++---- .../deque/deque_test_addAt5.wat | 8 +++---- .../deque/deque_test_addFirst.wat | 8 +++---- .../deque/deque_test_addLast.wat | 8 +++---- .../deque/deque_test_bufferExpansion.wat | 16 +++++++------- .../deque/deque_test_capacity.wat | 4 ++-- .../deque/deque_test_contains.wat | 6 ++--- .../deque/deque_test_copyDeep.wat | 8 +++---- .../deque/deque_test_copyShallow.wat | 8 +++---- .../deque/deque_test_filter1.wat | 10 ++++----- .../deque/deque_test_filter2.wat | 10 ++++----- .../deque/deque_test_filter3.wat | 6 ++--- .../deque/deque_test_filterMut1.wat | 10 ++++----- .../deque/deque_test_filterMut2.wat | 10 ++++----- .../deque/deque_test_filterMut3.wat | 6 ++--- .../deque/deque_test_getAt.wat | 4 ++-- .../deque/deque_test_getFirst.wat | 2 +- .../deque/deque_test_getLast.wat | 2 +- .../deque/deque_test_iterAdd.wat | 8 +++---- .../deque/deque_test_iterNext.wat | 4 ++-- .../deque/deque_test_iterRemove.wat | 6 ++--- .../deque/deque_test_removeAll.wat | 6 ++--- .../deque/deque_test_removeFirst.wat | 6 ++--- .../deque/deque_test_removeLast.wat | 6 ++--- .../deque/deque_test_reverse.wat | 6 ++--- .../deque/deque_test_size.wat | 2 +- .../deque/deque_test_trimCapacity.wat | 4 ++-- .../deque/deque_test_zipIterAdd.wat | 14 ++++++------ .../deque/deque_test_zipIterNext.wat | 10 ++++----- .../deque/deque_test_zipIterRemove.wat | 12 +++++----- .../deque/deque_test_zipIterReplace.wat | 8 +++---- .../list/list_test_add.wat | 12 +++++----- .../list/list_test_addAll.wat | 4 ++-- .../list/list_test_addAllAt.wat | 8 +++---- .../list/list_test_addAt.wat | 4 ++-- .../list/list_test_addFirst.wat | 8 +++---- .../list/list_test_addLast.wat | 8 +++---- .../list/list_test_contains.wat | 6 ++--- .../list/list_test_copyDeep.wat | 6 ++--- .../list/list_test_copyShallow.wat | 4 ++-- .../list/list_test_filter1.wat | 8 +++---- .../list/list_test_filter2.wat | 8 +++---- .../list/list_test_getAt.wat | 2 +- .../list/list_test_getLast.wat | 2 +- .../list/list_test_indexOf.wat | 4 ++-- .../list/list_test_iterAdd.wat | 8 +++---- .../list/list_test_iterDescAdd.wat | 10 ++++----- .../list/list_test_iterDescRemove.wat | 8 +++---- .../list/list_test_iterRemove.wat | 4 ++-- .../list/list_test_mutFilter1.wat | 8 +++---- .../list/list_test_mutFilter2.wat | 8 +++---- .../list/list_test_new.wat | 12 +++++----- .../list/list_test_remove.wat | 4 ++-- .../list/list_test_removeAll.wat | 6 ++--- .../list/list_test_removeAt.wat | 6 ++--- .../list/list_test_removeFirst.wat | 4 ++-- .../list/list_test_removeLast.wat | 6 ++--- .../list/list_test_replaceAt.wat | 2 +- .../list/list_test_reverse.wat | 6 ++--- .../list/list_test_sort.wat | 2 +- .../list/list_test_splice.wat | 10 ++++----- .../list/list_test_spliceAt.wat | 10 ++++----- .../list/list_test_sublist.wat | 4 ++-- .../list/list_test_toArray.wat | 2 +- .../list/list_test_zipIterAdd.wat | 22 +++++++++---------- .../list/list_test_zipIterNext.wat | 4 ++-- .../list/list_test_zipIterRemove.wat | 10 ++++----- .../list/list_test_zipIterReplace.wat | 12 +++++----- .../pqueue/pqueue_test_enqueue.wat | 8 +++---- .../pqueue/pqueue_test_pop.wat | 12 +++++----- .../queue/queue_test_enqueue.wat | 6 ++--- .../queue/queue_test_iter.wat | 6 ++--- .../queue/queue_test_poll.wat | 8 +++---- .../queue/queue_test_zipIterNext.wat | 10 ++++----- .../ring_buffer/ring_buffer_test_capacity.wat | 10 ++++----- .../ring_buffer/ring_buffer_test_dequeue.wat | 2 +- .../ring_buffer/ring_buffer_test_enqueue.wat | 2 +- .../slist/slist_test_add.wat | 12 +++++----- .../slist/slist_test_addAll.wat | 4 ++-- .../slist/slist_test_addAllAt.wat | 8 +++---- .../slist/slist_test_addAt.wat | 12 +++++----- .../slist/slist_test_addFirst.wat | 8 +++---- .../slist/slist_test_addLast.wat | 8 +++---- .../slist/slist_test_contains.wat | 6 ++--- .../slist/slist_test_copyDeep.wat | 6 ++--- .../slist/slist_test_copyShallow.wat | 8 +++---- .../slist/slist_test_filter1.wat | 6 ++--- .../slist/slist_test_filter2.wat | 10 ++++----- .../slist/slist_test_filter3.wat | 8 +++---- .../slist/slist_test_filterMut1.wat | 6 ++--- .../slist/slist_test_filterMut2.wat | 10 ++++----- .../slist/slist_test_filterMut3.wat | 4 ++-- .../slist/slist_test_get.wat | 2 +- .../slist/slist_test_getFirst.wat | 2 +- .../slist/slist_test_getLast.wat | 2 +- .../slist/slist_test_indexOf.wat | 4 ++-- .../slist/slist_test_iterAdd.wat | 10 ++++----- .../slist/slist_test_iterRemove.wat | 4 ++-- .../slist/slist_test_new.wat | 12 +++++----- .../slist/slist_test_remove.wat | 6 ++--- .../slist/slist_test_removeAll.wat | 4 ++-- .../slist/slist_test_removeAt.wat | 6 ++--- .../slist/slist_test_removeFirst.wat | 4 ++-- .../slist/slist_test_removeLast.wat | 4 ++-- .../slist/slist_test_replaceAt.wat | 2 +- .../slist/slist_test_reverse.wat | 2 +- .../slist/slist_test_splice.wat | 10 ++++----- .../slist/slist_test_spliceAt.wat | 10 ++++----- .../slist/slist_test_sublist.wat | 4 ++-- .../slist/slist_test_toArray.wat | 6 ++--- .../slist/slist_test_zipIterAdd.wat | 18 +++++++-------- .../slist/slist_test_zipIterNext.wat | 4 ++-- .../slist/slist_test_zipIterRemove.wat | 14 ++++++------ .../slist/slist_test_zipIterReplace.wat | 8 +++---- .../stack/stack_test_pop.wat | 4 ++-- .../stack/stack_test_push.wat | 6 ++--- .../treeset/treeset_test_add.wat | 6 ++--- .../treeset/treeset_test_iterNext.wat | 8 +++---- .../treeset/treeset_test_iterRemove.wat | 4 ++-- .../treeset/treeset_test_remove.wat | 4 ++-- .../treeset/treeset_test_removeAll.wat | 8 +++---- .../treeset/treeset_test_size.wat | 2 +- .../treetable/treetable_test_add.wat | 4 ++-- .../treetable/treetable_test_get.wat | 4 ++-- .../treetable/treetable_test_getFirst.wat | 2 +- .../treetable_test_getGreaterThan.wat | 2 +- .../treetable/treetable_test_getLast.wat | 2 +- .../treetable/treetable_test_getLessThan.wat | 2 +- .../treetable/treetable_test_iterNext.wat | 8 +++---- .../treetable/treetable_test_iterRemove.wat | 8 +++---- .../treetable/treetable_test_remove.wat | 2 +- .../treetable/treetable_test_removeAll.wat | 6 ++--- .../treetable/treetable_test_removeFirst.wat | 2 +- .../treetable/treetable_test_removeLast.wat | 2 +- .../treetable/treetable_test_size.wat | 2 +- 159 files changed, 516 insertions(+), 516 deletions(-) diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat index 4981b1449..9d7fa0445 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_add.wat @@ -28,7 +28,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 1028 call 0 @@ -94,7 +94,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 local.get 0 @@ -103,7 +103,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 local.get 0 @@ -112,7 +112,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat index ccc8a60c3..93d03f72c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat @@ -32,7 +32,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 8 i32.const 0 i32.load offset=1032 @@ -44,7 +44,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1032 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat index 0e592040d..2904464e1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -162,21 +162,21 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 local.get 0 i32.load i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat index db3364414..b60daf554 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat @@ -70,7 +70,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 0 @@ -87,7 +87,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 2 diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat index 05b4391fc..5d80399b0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat @@ -89,7 +89,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 local.get 0 @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat index 46d5eb478..8d6881434 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat @@ -80,14 +80,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=8 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat index 236775f11..48265915b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -166,7 +166,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 3 @@ -181,7 +181,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1040 @@ -192,7 +192,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 4 @@ -207,7 +207,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat index 5466fc79c..2e38e8f84 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -152,7 +152,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat index 9ef16ea31..ca25ac29d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -179,7 +179,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -190,7 +190,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat index 683bd5b1c..d8d0858de 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat @@ -129,7 +129,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -154,7 +154,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -202,7 +202,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat index 6fb4929b0..4577fc338 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -95,7 +95,7 @@ i32.lt_u i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1032 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat index f7298a50a..6b58bb8f5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -90,7 +90,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1032 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat index bcdeb4717..dcd812828 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat @@ -78,7 +78,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 i32.const 2 @@ -95,7 +95,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat index 0460a7c69..e3a305d0c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat @@ -84,7 +84,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.load @@ -93,7 +93,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat index 4561e64c8..33eee858b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat @@ -89,7 +89,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 local.get 0 @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=24 local.get 0 @@ -107,7 +107,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat index 4705f11b2..701321834 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat @@ -68,7 +68,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 i32.const 2 @@ -94,7 +94,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat index 3b6f2cc66..6522aed5f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat @@ -93,7 +93,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 i32.const 0 @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 32 i32.add @@ -135,7 +135,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 28 i32.add @@ -144,7 +144,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat index c26423cb3..c7d453e60 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -374,14 +374,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1052 @@ -395,14 +395,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -416,14 +416,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1048 @@ -434,7 +434,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -445,7 +445,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 5 i32.const 0 i32.load offset=1048 @@ -453,7 +453,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 4 i32.const 0 i32.load offset=1052 @@ -461,7 +461,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat index 54a1d66b4..019246ee0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat @@ -235,7 +235,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 call $array_destroy @@ -1183,7 +1183,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat index e1ce4f68e..3de6b5aea 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -255,7 +255,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -266,7 +266,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1044 @@ -274,7 +274,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 i32.const 0 i32.load offset=1048 @@ -282,7 +282,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 call $array_destroy @@ -1644,7 +1644,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat index c87cc583d..e9473587b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -382,14 +382,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=12 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1052 @@ -403,14 +403,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=12 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1048 @@ -421,7 +421,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -432,7 +432,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 call $array_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat index cca168a1d..f7d4f413e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat @@ -122,7 +122,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load offset=20 @@ -132,7 +132,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 @@ -146,7 +146,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat index 31374b79a..0000640a0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -140,7 +140,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -154,7 +154,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat index e502d1dbc..28617aed8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -140,7 +140,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -154,7 +154,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat index e20b84f64..ed3fab6b4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -140,7 +140,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -154,7 +154,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat index a759652d9..e269a7de1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -140,7 +140,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -154,7 +154,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat index 1ca6a09f4..dfb76bc16 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat @@ -70,7 +70,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.load offset=1036 @@ -101,7 +101,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=8 @@ -122,7 +122,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=8 @@ -143,7 +143,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat index 509c4b5b3..cb1f4473b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat @@ -70,7 +70,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.load offset=1036 @@ -89,7 +89,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 @@ -103,7 +103,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 @@ -117,7 +117,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat index 4c5f91305..6a112996a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1056 local.get 0 @@ -117,7 +117,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.load offset=1056 @@ -136,7 +136,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -150,7 +150,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -164,7 +164,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -178,7 +178,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=28 @@ -192,7 +192,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1056 local.get 0 @@ -213,7 +213,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat index d0aada4da..9c74d5fa9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat @@ -52,7 +52,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 1028 call 0 @@ -93,7 +93,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat index c485cf4d4..f694cc66f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat @@ -117,7 +117,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -126,7 +126,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1044 @@ -137,7 +137,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat index 3deef1f09..07c9a9fa6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat @@ -107,7 +107,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 i32.const 0 @@ -138,7 +138,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=24 local.get 0 @@ -147,7 +147,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 local.get 0 @@ -156,7 +156,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 i32.const 2 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat index dbeba7b03..8eda6a477 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat @@ -81,7 +81,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=28 i32.const 0 @@ -114,7 +114,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=36 local.get 0 @@ -123,7 +123,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=32 local.get 0 @@ -132,7 +132,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=28 call $deque_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat index b13e484b2..d50414862 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=16 @@ -187,7 +187,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=16 @@ -202,7 +202,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load offset=4 @@ -212,7 +212,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 @@ -226,7 +226,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 free diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat index 3fe5cbf3c..28bd2b9ec 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -171,7 +171,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=16 @@ -195,7 +195,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load @@ -205,7 +205,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load offset=4 @@ -215,7 +215,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load offset=8 @@ -225,7 +225,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 free diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat index e7a68b956..89e85da2b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -169,7 +169,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=16 @@ -193,7 +193,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.load @@ -203,7 +203,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=16 free diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat index 8143e6167..c67cf3304 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -168,7 +168,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 1 @@ -181,7 +181,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store @@ -198,7 +198,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -212,7 +212,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -226,7 +226,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat index c1a1829dc..d2ffd2f33 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -171,7 +171,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 1 @@ -184,7 +184,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store @@ -201,7 +201,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -215,7 +215,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -229,7 +229,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat index 178c32d61..abd4d87a3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -169,7 +169,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 i32.const 1 @@ -182,7 +182,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store @@ -199,7 +199,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat index d16a92133..16a426778 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat @@ -88,14 +88,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 8 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat index df59c5d70..7735a6d9b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat @@ -78,7 +78,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat index e7697d256..a2b1c9416 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat @@ -78,7 +78,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat index 956d10442..c7fea65a0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -173,7 +173,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 block ;; label = @1 loop ;; label = @2 local.get 0 @@ -229,7 +229,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end local.get 0 local.get 0 @@ -247,7 +247,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 4 @@ -264,7 +264,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat index 97d65dfe6..3852c5973 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -193,7 +193,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=20 @@ -207,7 +207,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 br 0 (;@2;) end end diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat index f2f77ccf0..a461c64c1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -208,7 +208,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 br 1 (;@3;) end i32.const 6 @@ -218,7 +218,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -240,7 +240,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat index 913d7f550..b0e27155c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat @@ -88,14 +88,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 8 local.get 0 i32.load i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -103,7 +103,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat index 7be1f58e0..cc1af4fb0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat @@ -89,7 +89,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -105,7 +105,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -121,7 +121,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat index 0d31c2fe9..2bedd592e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat @@ -89,7 +89,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -105,7 +105,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -121,7 +121,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat index cc7abc33a..14ab895f1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=20 local.get 0 @@ -107,7 +107,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=24 local.get 0 @@ -116,7 +116,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat index 451737f3e..168fe3fe1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat @@ -85,7 +85,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat index 01588bdcc..3363305eb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat @@ -68,7 +68,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 call $deque_trim_capacity @@ -80,7 +80,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat index a7cfa451a..ac25ffee0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -380,7 +380,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -397,7 +397,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -414,7 +414,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1044 @@ -425,7 +425,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=48 @@ -436,7 +436,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 5 i32.const 0 i32.load offset=1044 @@ -444,7 +444,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 4 local.get 0 i32.load offset=48 @@ -452,7 +452,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=48 call $deque_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat index 67f1ecf6e..b42c78a20 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -238,7 +238,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 54 i32.add @@ -249,7 +249,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -270,7 +270,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 38 i32.add @@ -281,7 +281,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end local.get 0 local.get 0 @@ -298,7 +298,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=32 call $deque_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat index 707d7cbac..30fdcbcb8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -350,7 +350,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 46 i32.add @@ -361,7 +361,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -372,7 +372,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -383,7 +383,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1044 @@ -391,7 +391,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=32 @@ -399,7 +399,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=32 call $deque_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat index 7fd25c05c..743eab7a3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -388,7 +388,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -405,7 +405,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1044 @@ -416,7 +416,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=64 @@ -427,7 +427,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=64 call $deque_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat index 9cbdb4f03..3cb1c433e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat @@ -84,7 +84,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -95,7 +95,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -106,7 +106,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -117,7 +117,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -131,7 +131,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -145,7 +145,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat index 3dae8062e..ba7e72119 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat @@ -208,7 +208,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -232,7 +232,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat index 7d72682f0..2b0df4b6f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 8 i32.const 0 i32.load offset=1044 @@ -217,7 +217,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -249,7 +249,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.load @@ -259,7 +259,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat index c2ec2ff3d..c0247d677 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat @@ -222,7 +222,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 3 @@ -240,7 +240,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat index a09cea0ff..59086cfa4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat @@ -85,7 +85,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -101,7 +101,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -116,7 +116,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -132,7 +132,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat index 476c523c5..d2fd68cec 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat @@ -85,7 +85,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -101,7 +101,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -116,7 +116,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -132,7 +132,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat index 05ffef0f5..965651e4e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1040 @@ -220,7 +220,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1040 @@ -231,7 +231,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=28 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat index d63bc10d3..15eb34e1d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat @@ -210,7 +210,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.const 2 @@ -236,7 +236,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.const 2 @@ -260,7 +260,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.const 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat index 927c16b60..4cbebd168 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat @@ -212,7 +212,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=12 @@ -253,7 +253,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat index cd759be1b..5d2c2eacd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -260,7 +260,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 local.get 0 i32.load offset=8 @@ -268,7 +268,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=4 @@ -285,7 +285,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 local.get 0 @@ -299,7 +299,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 free diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat index 0c9228bfd..5ab1d298e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -272,7 +272,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=8 @@ -280,7 +280,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 0 @@ -292,7 +292,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=4 i32.load @@ -301,7 +301,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat index fcb5f0af5..c503d1317 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat @@ -211,7 +211,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat index 0ddb7e546..ffd3c169c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat index 4d8241bb6..2e33f7b4f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -162,7 +162,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -180,7 +180,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=28 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat index 3524f9b02..0f69beedc 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -325,7 +325,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 3 @@ -343,7 +343,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 4 @@ -360,7 +360,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 32 i32.add @@ -433,7 +433,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=60 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat index 6f9a628d5..e6859bf50 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -349,7 +349,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -363,7 +363,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -377,7 +377,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 2 @@ -393,7 +393,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 4 @@ -409,7 +409,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=44 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat index be73df67a..72706e2c4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -317,7 +317,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -348,7 +348,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1064 local.get 0 @@ -357,7 +357,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1064 local.get 0 @@ -366,7 +366,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=44 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat index f665a9109..f11fe8c59 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -289,7 +289,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -299,7 +299,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=24 free diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat index 9051ef42d..c30811534 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -248,7 +248,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -261,7 +261,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=8 @@ -278,7 +278,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -292,7 +292,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat index cfc3368f6..25fd55b61 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -261,7 +261,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -274,7 +274,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 0 @@ -286,7 +286,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.load @@ -295,7 +295,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat index f8d8ed454..ebef17956 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat @@ -36,14 +36,14 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1032 i32.const 0 i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=12 @@ -60,7 +60,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1028 local.get 0 @@ -74,7 +74,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1028 @@ -82,7 +82,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1028 i32.const 0 @@ -90,7 +90,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat index 03cff88ba..4b27eb254 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -254,7 +254,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -264,7 +264,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 free diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat index 289e6a494..1b7aeaf6b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -222,7 +222,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=12 @@ -239,7 +239,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat index 77a9d8e95..b9a4403ee 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat @@ -222,7 +222,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1044 @@ -230,7 +230,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 0 @@ -258,7 +258,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat index 3aad1f1ff..f72fee0a0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat @@ -211,7 +211,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -227,7 +227,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat index 3385ce685..976a3cb97 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat @@ -211,7 +211,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -222,7 +222,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1060 local.get 0 @@ -231,7 +231,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat index 8bf7c52ae..e3e06c275 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat @@ -237,7 +237,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat index 4e51b41f3..c8f2a26c0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat @@ -221,7 +221,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -238,7 +238,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -253,7 +253,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat index 64eb5eb7d..8405dd79a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat @@ -120,7 +120,7 @@ i32.le_s i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat index 75f04e77a..8553c48f3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -217,7 +217,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -233,7 +233,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -249,7 +249,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 4 @@ -266,7 +266,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat index 0b49e62f4..ccbd90356 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat @@ -210,7 +210,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -218,7 +218,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -234,7 +234,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -250,7 +250,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -267,7 +267,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat index 8bdc587c2..a0ef0cc7b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat @@ -212,7 +212,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 i32.const 1 @@ -238,7 +238,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 call $list_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat index 38d7620b0..27faa5eb8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat @@ -240,7 +240,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat index dbfab160e..cbd7a7ae4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -704,14 +704,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=12 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1056 @@ -726,14 +726,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 local.get 0 i32.load offset=12 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1052 @@ -748,14 +748,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 local.get 0 i32.load offset=12 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -766,7 +766,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1056 @@ -777,7 +777,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 5 i32.const 0 i32.load offset=1052 @@ -785,7 +785,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 4 i32.const 0 i32.load offset=1056 @@ -793,7 +793,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 24 i32.add @@ -2259,7 +2259,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat index 145897352..687fbd9a6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat @@ -245,7 +245,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=108 @@ -1185,7 +1185,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat index f4468b4ce..e714dc4c6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -563,7 +563,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -574,7 +574,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1044 @@ -582,7 +582,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 i32.const 0 i32.load offset=1048 @@ -590,7 +590,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=108 @@ -1708,7 +1708,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat index c94b23b64..d859fed91 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -558,14 +558,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1052 @@ -580,14 +580,14 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=4 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1048 @@ -598,7 +598,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -609,7 +609,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.load offset=124 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat index a57ff9712..ebbc788e6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -221,7 +221,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -283,7 +283,7 @@ local.get 1 i32.const 1 i32.and - sym_assert + call 2 i32.const 0 local.set 1 block ;; label = @1 @@ -402,7 +402,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1056 @@ -486,7 +486,7 @@ local.get 1 i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat index 3645d7dd5..a2996e843 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -291,7 +291,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -307,7 +307,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -323,7 +323,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 local.get 0 i32.load offset=40 @@ -397,7 +397,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -409,7 +409,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -421,7 +421,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat index 8c00a011e..6cc6c56f8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat @@ -68,7 +68,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -84,7 +84,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -107,7 +107,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat index 0fe59babc..cacc5e03d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat @@ -162,21 +162,21 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=24 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=20 i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat index 51f2840b9..efa8e95e4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat @@ -83,7 +83,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -99,7 +99,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -115,7 +115,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -131,7 +131,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat index ba3a6c78f..bbcb2d909 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat @@ -204,7 +204,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 38 i32.add @@ -215,7 +215,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -236,7 +236,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 54 i32.add @@ -247,7 +247,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end local.get 0 local.get 0 @@ -264,7 +264,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 96 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat index 8a71dec20..5b18a0e7b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat @@ -263,7 +263,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=116 i32.const 0 @@ -273,7 +273,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 1026 call 0 @@ -318,7 +318,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 i32.const 1 @@ -329,7 +329,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -344,7 +344,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 160 diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat index b2553eca7..5752d39da 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat @@ -288,7 +288,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 12 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat index c14de4088..6f4360c97 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat @@ -284,7 +284,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load offset=12 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat index 1a08b8f91..7be263b6b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat @@ -87,7 +87,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -109,7 +109,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -120,7 +120,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -134,7 +134,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -148,7 +148,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 48 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat index 781137aeb..5c23ada09 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat @@ -209,7 +209,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -233,7 +233,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat index e0773d460..b9228e044 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat @@ -211,7 +211,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 8 i32.const 0 i32.load offset=1044 @@ -219,7 +219,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -235,7 +235,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 5 @@ -259,7 +259,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat index a60306c8e..333f60e75 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat @@ -224,7 +224,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 2 @@ -242,7 +242,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -253,7 +253,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -264,7 +264,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -281,7 +281,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -298,7 +298,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat index 15731525b..232be7e7e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat @@ -88,7 +88,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -104,7 +104,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -119,7 +119,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -135,7 +135,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat index eccbc2628..669d544a2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat @@ -88,7 +88,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -104,7 +104,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -119,7 +119,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 local.get 0 @@ -135,7 +135,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat index 7fbcadf5b..073ce1ee7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1040 @@ -109,7 +109,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1040 @@ -120,7 +120,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat index 82ec4a2d2..bb33d43ec 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat @@ -213,7 +213,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 2 @@ -237,7 +237,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -259,7 +259,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 2 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat index 9c9c163c4..9660d0db5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat @@ -211,7 +211,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 local.get 0 @@ -231,7 +231,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 local.get 0 @@ -251,7 +251,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 3 @@ -273,7 +273,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 call $slist_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat index b21ab3e7f..dd7811583 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -250,7 +250,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -266,7 +266,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=4 @@ -283,7 +283,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat index 836728e6a..4b8c47c78 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -249,7 +249,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -265,7 +265,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=12 @@ -305,7 +305,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -324,7 +324,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -336,7 +336,7 @@ i32.eqz br_if 0 (;@3;) i32.const 0 - sym_assert + call 2 end local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat index d0108a608..4f6c2eca5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -220,7 +220,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add @@ -254,7 +254,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 br 0 (;@2;) end end @@ -316,7 +316,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -332,7 +332,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat index 72615c060..5e045f1e6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -247,7 +247,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -260,7 +260,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=8 @@ -277,7 +277,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat index 857302bda..71b52877c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -246,7 +246,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -259,7 +259,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=4 @@ -299,7 +299,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -318,7 +318,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end block ;; label = @3 local.get 0 @@ -330,7 +330,7 @@ i32.eqz br_if 0 (;@3;) i32.const 0 - sym_assert + call 2 end local.get 0 local.get 0 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat index b4a5e599a..acc6ca258 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -247,7 +247,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 1 @@ -260,7 +260,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat index 4f2b6724f..0289b4b5f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat @@ -213,7 +213,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat index 769bbb924..21d0b3485 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat @@ -210,7 +210,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat index c64f55d70..a6f7cdd19 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat @@ -210,7 +210,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat index 674b3ad95..342b42f37 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat @@ -94,7 +94,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -111,7 +111,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat index d69fdadc8..92963ff83 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -328,7 +328,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 3 @@ -345,7 +345,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 i32.const 4 @@ -362,7 +362,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 1024 call 0 @@ -434,7 +434,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 6 i32.const 0 i32.load offset=1048 @@ -442,7 +442,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 64 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat index 9f0b74e87..69ab430f5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -289,7 +289,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -299,7 +299,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=40 free diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat index 19c3992ab..ccfd18671 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat @@ -47,14 +47,14 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 0 i32.ne i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=4 @@ -71,7 +71,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1028 local.get 0 @@ -85,7 +85,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1028 @@ -93,7 +93,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1028 local.get 0 @@ -101,7 +101,7 @@ i32.ne i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat index 784486903..50889a5c4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -242,7 +242,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -257,7 +257,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -267,7 +267,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 free diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat index 73ae3e524..d9c64fdab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat @@ -207,7 +207,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 0 i32.store offset=8 @@ -224,7 +224,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat index 02b74f15a..cdeafce38 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat @@ -224,7 +224,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1044 @@ -232,7 +232,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 0 @@ -260,7 +260,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat index de7db3992..dca459d9e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat @@ -213,7 +213,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -229,7 +229,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat index bc6f20c12..8cd32ce75 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat @@ -214,7 +214,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -230,7 +230,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat index 1eec1ffec..d76188995 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat @@ -234,7 +234,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat index fb76a5db1..7b3d7ddac 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat @@ -166,7 +166,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 local.get 0 i32.load diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat index c560c3c44..2bd9b4f96 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat @@ -210,7 +210,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -218,7 +218,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -234,7 +234,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -250,7 +250,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 4 @@ -267,7 +267,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat index 6988899c9..5652383c9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat @@ -212,7 +212,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1048 @@ -220,7 +220,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -236,7 +236,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 local.get 0 @@ -252,7 +252,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -269,7 +269,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 16 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat index a1084f79b..9942aaf36 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat @@ -213,7 +213,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 i32.const 1 @@ -237,7 +237,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 call $slist_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat index 2fdf3a436..078c74433 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat @@ -220,7 +220,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 2 @@ -237,7 +237,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 i32.const 3 @@ -254,7 +254,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=8 free diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat index 4b52e9943..047d7758a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -560,7 +560,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1056 local.get 0 @@ -577,7 +577,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -594,7 +594,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -605,7 +605,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1056 @@ -616,7 +616,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 5 i32.const 0 i32.load offset=1052 @@ -624,7 +624,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 4 i32.const 0 i32.load offset=1056 @@ -632,7 +632,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 16 i32.add @@ -695,7 +695,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -709,7 +709,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 144 diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat index c64adff86..0c833ec7a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -343,7 +343,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 112 @@ -1202,7 +1202,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat index bbb5b52d7..a94015457 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -446,7 +446,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1052 @@ -457,7 +457,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 3 i32.const 0 i32.load offset=1048 @@ -465,7 +465,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 2 i32.const 0 i32.load offset=1052 @@ -473,7 +473,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.const 32 i32.add @@ -559,7 +559,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 7 i32.const 0 i32.load offset=1052 @@ -570,7 +570,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1048 local.get 0 @@ -1800,7 +1800,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 2 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat index 3513e47a6..2e6c2dc4e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -544,7 +544,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1052 local.get 0 @@ -561,7 +561,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1052 @@ -572,7 +572,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1056 @@ -583,7 +583,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_test local.get 0 i32.const 160 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat index b51ac5196..a44a06ac9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat @@ -76,7 +76,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -92,7 +92,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat index 3fcbfc0e9..223d561d0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat @@ -62,7 +62,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -85,7 +85,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1036 local.get 0 @@ -108,7 +108,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 call $teardown_tests local.get 0 i32.const 32 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat index f1cdaa861..8f26c9bba 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -100,7 +100,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1036 @@ -111,7 +111,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1036 @@ -122,7 +122,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat index b5f4c7bab..78007bb05 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -215,28 +215,28 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=36 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=32 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=28 i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=60 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat index 7d78687f8..e69de2c38 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -140,7 +140,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -151,7 +151,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=44 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat index bcdf07641..a7b71a0b4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -104,7 +104,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -115,7 +115,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat index 1ff68a514..eb45b9e47 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -98,7 +98,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -109,7 +109,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -120,7 +120,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1036 @@ -129,7 +129,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat index 187c62750..5184be16f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -95,7 +95,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 local.set 1 diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat index 3b061b209..83dc96716 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -121,7 +121,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 i32.const 0 i32.load offset=1040 @@ -132,7 +132,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat index f1615b826..5b92e8158 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -112,7 +112,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 local.get 0 i32.load offset=12 local.get 0 @@ -123,7 +123,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat index 6c577bf49..9acbb1fd7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -172,7 +172,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat index a32b702ba..530c23af9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -175,7 +175,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat index 17fbcfb43..e213af8d9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -172,7 +172,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat index dc661735d..09e35d9d4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -175,7 +175,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat index b56cd145a..8d5b5f43d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -275,28 +275,28 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=36 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=32 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 1 local.get 0 i32.load offset=28 i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat index 1aaf3ec81..c956d7dbf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -167,7 +167,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 6 local.get 0 i32.const 24 @@ -177,7 +177,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 end br 0 (;@2;) end @@ -189,7 +189,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1040 @@ -200,7 +200,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat index 90318582c..ee4a348db 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -144,7 +144,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat index 96f73c29d..a0b03810f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat @@ -112,7 +112,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -123,7 +123,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.const 0 i32.load offset=1044 @@ -134,7 +134,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat index acf46d15c..ce72731c4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -173,7 +173,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat index 9c631efcc..9b80c7a00 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -173,7 +173,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1044 call $treetable_destroy diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat index 316ff4e65..bd2721677 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -139,7 +139,7 @@ i32.eq i32.const 1 i32.and - sym_assert + call 2 i32.const 0 i32.load offset=1040 call $treetable_destroy From 1fce3a4080950762121adf23a2cca71b755d83fd Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 11:37:56 -0500 Subject: [PATCH 096/105] alloc and free wasp primitive --- .../array/array_test_addAt2.wat | 10 ++++++---- .../array/array_test_contains.wat | 10 ++++++---- .../array/array_test_deepCopy.wat | 10 ++++++---- .../array/array_test_getAt.wat | 10 ++++++---- .../array/array_test_indexOf.wat | 10 ++++++---- .../array/array_test_iterAdd.wat | 10 ++++++---- .../array/array_test_iterRemove.wat | 10 ++++++---- .../array/array_test_iterReplace.wat | 10 ++++++---- .../array/array_test_reduce.wat | 10 ++++++---- .../array/array_test_remove.wat | 10 ++++++---- .../array/array_test_removeAll.wat | 14 ++++++++------ .../array/array_test_removeAt.wat | 10 ++++++---- .../array/array_test_replaceAt.wat | 10 ++++++---- .../array/array_test_reverse.wat | 10 ++++++---- .../array/array_test_shallowCopy.wat | 10 ++++++---- .../array/array_test_subarray.wat | 10 ++++++---- .../array/array_test_zipIterAdd.wat | 10 ++++++---- .../array/array_test_zipIterNext.wat | 10 ++++++---- .../array/array_test_zipIterRemove.wat | 10 ++++++---- .../array/array_test_zipIterReplace.wat | 10 ++++++---- .../deque/deque_test_addAt1.wat | 10 ++++++---- .../deque/deque_test_addAt2.wat | 10 ++++++---- .../deque/deque_test_addAt3.wat | 10 ++++++---- .../deque/deque_test_addAt4.wat | 10 ++++++---- .../deque/deque_test_addAt5.wat | 10 ++++++---- .../deque/deque_test_addFirst.wat | 10 ++++++---- .../deque/deque_test_addLast.wat | 10 ++++++---- .../deque/deque_test_bufferExpansion.wat | 10 ++++++---- .../deque/deque_test_capacity.wat | 10 ++++++---- .../deque/deque_test_contains.wat | 10 ++++++---- .../deque/deque_test_copyDeep.wat | 16 +++++++++------- .../deque/deque_test_copyShallow.wat | 10 ++++++---- .../deque/deque_test_filter1.wat | 12 +++++++----- .../deque/deque_test_filter2.wat | 12 +++++++----- .../deque/deque_test_filter3.wat | 12 +++++++----- .../deque/deque_test_filterMut1.wat | 10 ++++++---- .../deque/deque_test_filterMut2.wat | 10 ++++++---- .../deque/deque_test_filterMut3.wat | 10 ++++++---- .../deque/deque_test_getAt.wat | 10 ++++++---- .../deque/deque_test_getFirst.wat | 10 ++++++---- .../deque/deque_test_getLast.wat | 10 ++++++---- .../deque/deque_test_iterAdd.wat | 10 ++++++---- .../deque/deque_test_iterNext.wat | 10 ++++++---- .../deque/deque_test_iterRemove.wat | 10 ++++++---- .../deque/deque_test_removeAll.wat | 10 ++++++---- .../deque/deque_test_removeFirst.wat | 10 ++++++---- .../deque/deque_test_removeLast.wat | 10 ++++++---- .../deque/deque_test_reverse.wat | 10 ++++++---- .../deque/deque_test_size.wat | 10 ++++++---- .../deque/deque_test_trimCapacity.wat | 10 ++++++---- .../deque/deque_test_zipIterAdd.wat | 10 ++++++---- .../deque/deque_test_zipIterNext.wat | 10 ++++++---- .../deque/deque_test_zipIterRemove.wat | 10 ++++++---- .../deque/deque_test_zipIterReplace.wat | 10 ++++++---- .../Collection-C-normal/list/list_test_add.wat | 10 ++++++---- .../list/list_test_addAll.wat | 10 ++++++---- .../list/list_test_addAllAt.wat | 10 ++++++---- .../Collection-C-normal/list/list_test_addAt.wat | 10 ++++++---- .../list/list_test_addFirst.wat | 10 ++++++---- .../list/list_test_addLast.wat | 10 ++++++---- .../list/list_test_contains.wat | 10 ++++++---- .../list/list_test_copyDeep.wat | 10 ++++++---- .../list/list_test_copyShallow.wat | 10 ++++++---- .../list/list_test_filter1.wat | 12 +++++++----- .../list/list_test_filter2.wat | 10 ++++++---- .../Collection-C-normal/list/list_test_getAt.wat | 10 ++++++---- .../list/list_test_getLast.wat | 10 ++++++---- .../list/list_test_indexOf.wat | 10 ++++++---- .../list/list_test_iterAdd.wat | 10 ++++++---- .../list/list_test_iterDescAdd.wat | 10 ++++++---- .../list/list_test_iterDescRemove.wat | 12 +++++++----- .../list/list_test_iterRemove.wat | 12 +++++++----- .../list/list_test_mutFilter1.wat | 10 ++++++---- .../list/list_test_mutFilter2.wat | 10 ++++++---- .../Collection-C-normal/list/list_test_new.wat | 10 ++++++---- .../list/list_test_remove.wat | 12 +++++++----- .../list/list_test_removeAll.wat | 10 ++++++---- .../list/list_test_removeAt.wat | 14 ++++++++------ .../list/list_test_removeFirst.wat | 12 +++++++----- .../list/list_test_removeLast.wat | 12 +++++++----- .../list/list_test_replaceAt.wat | 12 +++++++----- .../list/list_test_reverse.wat | 10 ++++++---- .../Collection-C-normal/list/list_test_sort.wat | 10 ++++++---- .../list/list_test_splice.wat | 10 ++++++---- .../list/list_test_spliceAt.wat | 10 ++++++---- .../list/list_test_sublist.wat | 10 ++++++---- .../list/list_test_toArray.wat | 12 +++++++----- .../list/list_test_zipIterAdd.wat | 10 ++++++---- .../list/list_test_zipIterNext.wat | 10 ++++++---- .../list/list_test_zipIterRemove.wat | 10 ++++++---- .../list/list_test_zipIterReplace.wat | 10 ++++++---- .../pqueue/pqueue_test_enqueue.wat | 10 ++++++---- .../pqueue/pqueue_test_pop.wat | 10 ++++++---- .../queue/queue_test_enqueue.wat | 10 ++++++---- .../queue/queue_test_iter.wat | 10 ++++++---- .../queue/queue_test_poll.wat | 10 ++++++---- .../queue/queue_test_zipIterNext.wat | 10 ++++++---- .../ring_buffer/ring_buffer_test_capacity.wat | 10 ++++++---- .../ring_buffer/ring_buffer_test_dequeue.wat | 10 ++++++---- .../ring_buffer/ring_buffer_test_enqueue.wat | 10 ++++++---- .../Collection-C-normal/slist/slist_test_add.wat | 10 ++++++---- .../slist/slist_test_addAll.wat | 10 ++++++---- .../slist/slist_test_addAllAt.wat | 10 ++++++---- .../slist/slist_test_addAt.wat | 10 ++++++---- .../slist/slist_test_addFirst.wat | 10 ++++++---- .../slist/slist_test_addLast.wat | 10 ++++++---- .../slist/slist_test_contains.wat | 10 ++++++---- .../slist/slist_test_copyDeep.wat | 10 ++++++---- .../slist/slist_test_copyShallow.wat | 10 ++++++---- .../slist/slist_test_filter1.wat | 10 ++++++---- .../slist/slist_test_filter2.wat | 10 ++++++---- .../slist/slist_test_filter3.wat | 10 ++++++---- .../slist/slist_test_filterMut1.wat | 10 ++++++---- .../slist/slist_test_filterMut2.wat | 10 ++++++---- .../slist/slist_test_filterMut3.wat | 10 ++++++---- .../Collection-C-normal/slist/slist_test_get.wat | 10 ++++++---- .../slist/slist_test_getFirst.wat | 10 ++++++---- .../slist/slist_test_getLast.wat | 10 ++++++---- .../slist/slist_test_indexOf.wat | 10 ++++++---- .../slist/slist_test_iterAdd.wat | 10 ++++++---- .../slist/slist_test_iterRemove.wat | 12 +++++++----- .../Collection-C-normal/slist/slist_test_new.wat | 10 ++++++---- .../slist/slist_test_remove.wat | 12 +++++++----- .../slist/slist_test_removeAll.wat | 10 ++++++---- .../slist/slist_test_removeAt.wat | 14 ++++++++------ .../slist/slist_test_removeFirst.wat | 12 +++++++----- .../slist/slist_test_removeLast.wat | 12 +++++++----- .../slist/slist_test_replaceAt.wat | 12 +++++++----- .../slist/slist_test_reverse.wat | 10 ++++++---- .../slist/slist_test_splice.wat | 10 ++++++---- .../slist/slist_test_spliceAt.wat | 10 ++++++---- .../slist/slist_test_sublist.wat | 10 ++++++---- .../slist/slist_test_toArray.wat | 12 +++++++----- .../slist/slist_test_zipIterAdd.wat | 10 ++++++---- .../slist/slist_test_zipIterNext.wat | 10 ++++++---- .../slist/slist_test_zipIterRemove.wat | 10 ++++++---- .../slist/slist_test_zipIterReplace.wat | 10 ++++++---- .../Collection-C-normal/stack/stack_test_pop.wat | 10 ++++++---- .../stack/stack_test_push.wat | 10 ++++++---- .../treeset/treeset_test_add.wat | 10 ++++++---- .../treeset/treeset_test_iterNext.wat | 10 ++++++---- .../treeset/treeset_test_iterRemove.wat | 10 ++++++---- .../treeset/treeset_test_remove.wat | 10 ++++++---- .../treeset/treeset_test_removeAll.wat | 10 ++++++---- .../treeset/treeset_test_size.wat | 10 ++++++---- .../treetable/treetable_test_add.wat | 10 ++++++---- .../treetable/treetable_test_get.wat | 10 ++++++---- .../treetable/treetable_test_getFirst.wat | 10 ++++++---- .../treetable/treetable_test_getGreaterThan.wat | 10 ++++++---- .../treetable/treetable_test_getLast.wat | 10 ++++++---- .../treetable/treetable_test_getLessThan.wat | 10 ++++++---- .../treetable/treetable_test_iterNext.wat | 10 ++++++---- .../treetable/treetable_test_iterRemove.wat | 10 ++++++---- .../treetable/treetable_test_remove.wat | 10 ++++++---- .../treetable/treetable_test_removeAll.wat | 10 ++++++---- .../treetable/treetable_test_removeFirst.wat | 10 ++++++---- .../treetable/treetable_test_removeLast.wat | 10 ++++++---- .../treetable/treetable_test_size.wat | 10 ++++++---- 158 files changed, 974 insertions(+), 658 deletions(-) diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat index 93d03f72c..953891da9 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_addAt2.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -736,7 +738,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -810,7 +812,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -829,7 +831,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat index 2904464e1..ad83e7f65 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_contains.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -763,7 +765,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -837,7 +839,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -856,7 +858,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat index b60daf554..38429cc0e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_deepCopy.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -898,7 +900,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -972,7 +974,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -991,7 +993,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat index 5d80399b0..9ca50f5e8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_getAt.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -670,7 +672,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -744,7 +746,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -763,7 +765,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat index 8d6881434..a72630d29 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_indexOf.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -682,7 +684,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -756,7 +758,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -775,7 +777,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat index 48265915b..f8d4b58d6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterAdd.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1137,7 +1139,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1211,7 +1213,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1230,7 +1232,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat index 2e38e8f84..db56de31f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterRemove.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1000,7 +1002,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1074,7 +1076,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1093,7 +1095,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat index ca25ac29d..9d2208264 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_iterReplace.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1043,7 +1045,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1117,7 +1119,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1136,7 +1138,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat index d8d0858de..53e62556e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reduce.wat @@ -74,7 +74,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -833,7 +835,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -907,7 +909,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -926,7 +928,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat index 4577fc338..3f765c6c8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_remove.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -825,7 +827,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -899,7 +901,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -918,7 +920,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat index 6b58bb8f5..67a286185 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAll.wat @@ -4,10 +4,12 @@ (type (;2;) (func (param i32))) (type (;3;) (func (result i32))) (type (;4;) (func (param i32 i32 i32) (result i32))) - (import "i32" "symbolic" (func (;0;) (type 0))) - (import "i32" "sym_assume" (func (;1;) (type 1))) - (import "i32" "sym_assert" (func (;2;) (type 1))) + (import "i32" "symbolic" (func (;0;) (type 1))) + (import "i32" "sym_assume" (func (;1;) (type 2))) + (import "i32" "sym_assert" (func (;2;) (type 2))) (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -636,7 +638,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -710,7 +712,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -729,7 +731,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat index dcd812828..e1de2f881 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_removeAt.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -801,7 +803,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -875,7 +877,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -894,7 +896,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat index e3a305d0c..7a89db927 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_replaceAt.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -738,7 +740,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -812,7 +814,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -831,7 +833,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat index 33eee858b..5b9b5b766 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_reverse.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -768,7 +770,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -842,7 +844,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -861,7 +863,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat index 701321834..f8c3df0d3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_shallowCopy.wat @@ -7,7 +7,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -811,7 +813,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -885,7 +887,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -904,7 +906,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat index 6522aed5f..a2143b4ca 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_subarray.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -898,7 +900,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -972,7 +974,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -991,7 +993,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat index c7d453e60..dcc8dc546 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterAdd.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1619,7 +1621,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1693,7 +1695,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1712,7 +1714,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat index 019246ee0..e13a79336 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterNext.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -980,7 +982,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1054,7 +1056,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1073,7 +1075,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat index 3de6b5aea..e7d8e1bc5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterRemove.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1327,7 +1329,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1401,7 +1403,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1420,7 +1422,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat index e9473587b..4eaaedd89 100644 --- a/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/array/array_test_zipIterReplace.wat @@ -10,7 +10,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1484,7 +1486,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1558,7 +1560,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1577,7 +1579,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat index f7d4f413e..c5db213ce 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt1.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -208,7 +210,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -282,7 +284,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -301,7 +303,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat index 0000640a0..e1ff4a51c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt2.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -230,7 +232,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -304,7 +306,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -323,7 +325,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat index 28617aed8..5786e83ac 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt3.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -230,7 +232,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -304,7 +306,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -323,7 +325,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat index ed3fab6b4..f582fa0b6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt4.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -230,7 +232,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -304,7 +306,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -323,7 +325,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat index e269a7de1..5a0d3e9dd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addAt5.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -230,7 +232,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -304,7 +306,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -323,7 +325,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat index dfb76bc16..611b44929 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addFirst.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -205,7 +207,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -279,7 +281,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -298,7 +300,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat index cb1f4473b..3beb0a614 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_addLast.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -179,7 +181,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -253,7 +255,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -272,7 +274,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat index 6a112996a..a148d47ee 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_bufferExpansion.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -275,7 +277,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -349,7 +351,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -368,7 +370,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat index 9c74d5fa9..8fcc078d3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_capacity.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -155,7 +157,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -229,7 +231,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -248,7 +250,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat index f694cc66f..e7e49fbe2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_contains.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -199,7 +201,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -273,7 +275,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -292,7 +294,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat index 07c9a9fa6..2c21c9f14 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyDeep.wat @@ -19,7 +19,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -163,13 +165,13 @@ call $deque_destroy_cb local.get 0 i32.load offset=40 - free + call 5 local.get 0 i32.load offset=36 - free + call 5 local.get 0 i32.load offset=32 - free + call 5 call $teardown_tests local.get 0 i32.const 48 @@ -231,7 +233,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -305,7 +307,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -324,7 +326,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat index 8eda6a477..5fceef6b2 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_copyShallow.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -197,7 +199,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -271,7 +273,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -290,7 +292,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat index d50414862..858e8dca0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter1.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -229,7 +231,7 @@ call 2 local.get 0 i32.load offset=16 - free + call 5 call $teardown_tests local.get 0 i32.const 48 @@ -291,7 +293,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -365,7 +367,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -384,7 +386,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat index 28bd2b9ec..1edb393cf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter2.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -228,7 +230,7 @@ call 2 local.get 0 i32.load offset=16 - free + call 5 call $teardown_tests local.get 0 i32.const 48 @@ -290,7 +292,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -364,7 +366,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -383,7 +385,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat index 89e85da2b..25f755fc4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filter3.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -206,7 +208,7 @@ call 2 local.get 0 i32.load offset=16 - free + call 5 call $teardown_tests local.get 0 i32.const 48 @@ -268,7 +270,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -342,7 +344,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -361,7 +363,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat index c67cf3304..cd1e9402f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut1.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -288,7 +290,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -362,7 +364,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -381,7 +383,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat index d2ffd2f33..7a05d4d06 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut2.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -291,7 +293,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -365,7 +367,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -384,7 +386,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat index abd4d87a3..2c1498575 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_filterMut3.wat @@ -33,7 +33,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -261,7 +263,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -335,7 +337,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -354,7 +356,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat index 16a426778..348fc5335 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getAt.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -157,7 +159,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -231,7 +233,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -250,7 +252,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat index 7735a6d9b..f622cfc84 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getFirst.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -140,7 +142,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -214,7 +216,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -233,7 +235,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat index a2b1c9416..7d21853ea 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_getLast.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -140,7 +142,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -214,7 +216,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -233,7 +235,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat index c7fea65a0..f6ddbde95 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterAdd.wat @@ -19,7 +19,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -326,7 +328,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -400,7 +402,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -419,7 +421,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat index 3852c5973..32742da33 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterNext.wat @@ -19,7 +19,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -272,7 +274,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -346,7 +348,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -365,7 +367,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat index a461c64c1..f3029b9e4 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_iterRemove.wat @@ -19,7 +19,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -312,7 +314,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -386,7 +388,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -405,7 +407,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat index b0e27155c..18c1cf6ca 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeAll.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -165,7 +167,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -239,7 +241,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -258,7 +260,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat index cc1af4fb0..43347be1b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeFirst.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -183,7 +185,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -257,7 +259,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -276,7 +278,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat index 2bedd592e..e1129bc37 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_removeLast.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -183,7 +185,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -257,7 +259,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -276,7 +278,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat index 14ab895f1..c09fe70cf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_reverse.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -178,7 +180,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -252,7 +254,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -271,7 +273,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat index 168fe3fe1..a4ea6bd77 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_size.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -147,7 +149,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -221,7 +223,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -240,7 +242,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat index 3363305eb..022703733 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_trimCapacity.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -142,7 +144,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -216,7 +218,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -235,7 +237,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat index ac25ffee0..88a1a05f5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterAdd.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -612,7 +614,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -686,7 +688,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -705,7 +707,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat index b42c78a20..e074cf6b8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterNext.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -458,7 +460,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -532,7 +534,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -551,7 +553,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat index 30fdcbcb8..878921070 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterRemove.wat @@ -18,7 +18,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -559,7 +561,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -633,7 +635,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -652,7 +654,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat index 743eab7a3..3d4fb1fd1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/deque/deque_test_zipIterReplace.wat @@ -20,7 +20,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -587,7 +589,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -661,7 +663,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -680,7 +682,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat index 3cb1c433e..bc896e3e1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_add.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -207,7 +209,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -281,7 +283,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -300,7 +302,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat index ba7e72119..d75f7c42c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAll.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -294,7 +296,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -368,7 +370,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -387,7 +389,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat index 2b0df4b6f..8de9b6374 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAllAt.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -321,7 +323,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -395,7 +397,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -414,7 +416,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat index c0247d677..4cbea7606 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addAt.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -302,7 +304,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -376,7 +378,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -395,7 +397,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat index 59086cfa4..f962e7c42 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addFirst.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -194,7 +196,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -268,7 +270,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -287,7 +289,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat index d2fd68cec..d51b29476 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_addLast.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -194,7 +196,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -268,7 +270,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -287,7 +289,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat index 965651e4e..0f982140d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_contains.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -296,7 +298,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -370,7 +372,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -389,7 +391,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat index 15eb34e1d..e3b8c7c55 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyDeep.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -326,7 +328,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -400,7 +402,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -419,7 +421,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat index 4cbebd168..262b0a371 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_copyShallow.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -327,7 +329,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -401,7 +403,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -420,7 +422,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat index 5d2c2eacd..a8a35a7b1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter1.wat @@ -201,7 +201,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -302,7 +304,7 @@ call 2 local.get 0 i32.load offset=8 - free + call 5 call $teardown_test local.get 0 i32.load offset=12 @@ -367,7 +369,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -441,7 +443,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -460,7 +462,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat index 5ab1d298e..9d004efab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_filter2.wat @@ -201,7 +201,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -366,7 +368,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -440,7 +442,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -459,7 +461,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat index c503d1317..b89468ec3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getAt.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -273,7 +275,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -347,7 +349,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -366,7 +368,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat index ffd3c169c..ae2c80004 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_getLast.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -271,7 +273,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -345,7 +347,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -364,7 +366,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat index 2e33f7b4f..fb201dc76 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_indexOf.wat @@ -22,7 +22,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -245,7 +247,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -319,7 +321,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -338,7 +340,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat index 0f69beedc..941b273f5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterAdd.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -498,7 +500,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -572,7 +574,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -591,7 +593,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat index e6859bf50..f3fb296ae 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescAdd.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -474,7 +476,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -548,7 +550,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -567,7 +569,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat index 72706e2c4..d5c662325 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterDescRemove.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -305,7 +307,7 @@ drop local.get 0 i32.load offset=20 - free + call 5 end br 0 (;@2;) end @@ -431,7 +433,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -505,7 +507,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -524,7 +526,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat index f11fe8c59..4ff94d304 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_iterRemove.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -302,7 +304,7 @@ call 2 local.get 0 i32.load offset=24 - free + call 5 call $teardown_test local.get 0 i32.load offset=28 @@ -367,7 +369,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -441,7 +443,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -460,7 +462,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat index c30811534..60891a280 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter1.wat @@ -200,7 +200,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -357,7 +359,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -431,7 +433,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -450,7 +452,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat index 25fd55b61..c8941f6b1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_mutFilter2.wat @@ -201,7 +201,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -360,7 +362,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -434,7 +436,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -453,7 +455,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat index ebef17956..840afc807 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_new.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -152,7 +154,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -226,7 +228,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -245,7 +247,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat index 4b27eb254..d4aec2e21 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_remove.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -267,7 +269,7 @@ call 2 local.get 0 i32.load offset=8 - free + call 5 call $teardown_test local.get 0 i32.load offset=12 @@ -332,7 +334,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -406,7 +408,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -425,7 +427,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat index 1b7aeaf6b..ff61bcbba 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAll.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -301,7 +303,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -375,7 +377,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -394,7 +396,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat index b9a4403ee..b3159fd29 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeAt.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -205,7 +207,7 @@ drop local.get 0 i32.load offset=12 - free + call 5 i32.const 0 i32.load offset=1044 i32.const 2 @@ -241,7 +243,7 @@ drop local.get 0 i32.load offset=12 - free + call 5 i32.const 0 i32.load offset=1044 i32.const 0 @@ -320,7 +322,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -394,7 +396,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -413,7 +415,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat index f72fee0a0..132e492ab 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeFirst.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -203,7 +205,7 @@ drop local.get 0 i32.load offset=12 - free + call 5 i32.const 3 i32.const 0 i32.load offset=1044 @@ -289,7 +291,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -363,7 +365,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -382,7 +384,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat index 976a3cb97..b0af84e7d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_removeLast.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -203,7 +205,7 @@ drop local.get 0 i32.load offset=12 - free + call 5 i32.const 3 i32.const 0 i32.load offset=1044 @@ -293,7 +295,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -367,7 +369,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -386,7 +388,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat index e3e06c275..a96885ee8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_replaceAt.wat @@ -187,7 +187,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -221,7 +223,7 @@ drop local.get 0 i32.load offset=4 - free + call 5 i32.const 0 i32.load offset=1048 i32.const 2 @@ -299,7 +301,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -373,7 +375,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -392,7 +394,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat index c8f2a26c0..cc7137dd0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_reverse.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -315,7 +317,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -389,7 +391,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -408,7 +410,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat index 8405dd79a..c1bc94755 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sort.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -252,7 +254,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -326,7 +328,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -345,7 +347,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat index 8553c48f3..d31f8b929 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_splice.wat @@ -187,7 +187,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -328,7 +330,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -402,7 +404,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -421,7 +423,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat index ccbd90356..d977d4613 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_spliceAt.wat @@ -187,7 +187,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -329,7 +331,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -403,7 +405,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -422,7 +424,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat index a0ef0cc7b..db46acfdd 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_sublist.wat @@ -187,7 +187,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -303,7 +305,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -377,7 +379,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -396,7 +398,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat index 27faa5eb8..384391750 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_toArray.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -252,7 +254,7 @@ end local.get 0 i32.load offset=8 - free + call 5 call $teardown_test local.get 0 i32.load offset=12 @@ -317,7 +319,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -391,7 +393,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -410,7 +412,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat index cbd7a7ae4..0358c1875 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterAdd.wat @@ -25,7 +25,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -1028,7 +1030,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -1102,7 +1104,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -1121,7 +1123,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat index 687fbd9a6..6ae57ab26 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterNext.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -405,7 +407,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -479,7 +481,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -498,7 +500,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat index e714dc4c6..89ebbf04b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterRemove.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -750,7 +752,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -824,7 +826,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -843,7 +845,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat index d859fed91..e58fcefd5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/list/list_test_zipIterReplace.wat @@ -25,7 +25,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -769,7 +771,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -843,7 +845,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -862,7 +864,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat index ebbc788e6..af25cc89c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_enqueue.wat @@ -121,7 +121,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -548,7 +550,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -622,7 +624,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -641,7 +643,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat index a2996e843..d5b868e28 100644 --- a/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/pqueue/pqueue_test_pop.wat @@ -121,7 +121,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -483,7 +485,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -557,7 +559,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -576,7 +578,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat index 6cc6c56f8..3b74f3b39 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_enqueue.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -169,7 +171,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -243,7 +245,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -262,7 +264,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat index cacc5e03d..f65b57db5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_iter.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -238,7 +240,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -312,7 +314,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -331,7 +333,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat index efa8e95e4..174705585 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_poll.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -193,7 +195,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -267,7 +269,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -286,7 +288,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat index bbcb2d909..7439bf9e6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/queue/queue_test_zipIterNext.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -421,7 +423,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -495,7 +497,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -514,7 +516,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat index 5b18a0e7b..a48be8907 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_capacity.wat @@ -16,7 +16,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -406,7 +408,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -480,7 +482,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -499,7 +501,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat index 5752d39da..cb92f968e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_dequeue.wat @@ -16,7 +16,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -364,7 +366,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -438,7 +440,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -457,7 +459,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat index 6f4360c97..7edd6f10a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat +++ b/benchmarks/pldi2026/Collection-C-normal/ring_buffer/ring_buffer_test_enqueue.wat @@ -16,7 +16,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -355,7 +357,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -429,7 +431,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -448,7 +450,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat index 7be263b6b..0247db330 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_add.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -210,7 +212,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -284,7 +286,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -303,7 +305,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat index 5c23ada09..ba67bbfd7 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAll.wat @@ -184,7 +184,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -295,7 +297,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -369,7 +371,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -388,7 +390,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat index b9228e044..da979fbc5 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAllAt.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -321,7 +323,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -395,7 +397,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -414,7 +416,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat index 333f60e75..c52a5b385 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addAt.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -360,7 +362,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -434,7 +436,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -453,7 +455,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat index 232be7e7e..cba5b8f4c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addFirst.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -197,7 +199,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -271,7 +273,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -290,7 +292,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat index 669d544a2..68bf82471 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_addLast.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -197,7 +199,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -271,7 +273,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -290,7 +292,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat index 073ce1ee7..92f2e335f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_contains.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -182,7 +184,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -256,7 +258,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -275,7 +277,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat index bb33d43ec..c129613af 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyDeep.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -325,7 +327,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -399,7 +401,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -418,7 +420,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat index 9660d0db5..589282cec 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_copyShallow.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -338,7 +340,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -412,7 +414,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -431,7 +433,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat index dd7811583..aba3c6e2a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter1.wat @@ -199,7 +199,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -345,7 +347,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -419,7 +421,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -438,7 +440,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat index 4b8c47c78..f54242881 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter2.wat @@ -200,7 +200,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -408,7 +410,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -482,7 +484,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -501,7 +503,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat index 4f6c2eca5..db8c4eda0 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filter3.wat @@ -265,7 +265,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 5) (result i32) (local i32 i32) global.get 0 @@ -399,7 +401,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -473,7 +475,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -492,7 +494,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat index 5e045f1e6..957c3c64a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut1.wat @@ -199,7 +199,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -339,7 +341,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -413,7 +415,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -432,7 +434,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat index 71b52877c..bee22b572 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut2.wat @@ -200,7 +200,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -402,7 +404,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -476,7 +478,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -495,7 +497,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat index acc6ca258..42ca07048 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_filterMut3.wat @@ -199,7 +199,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32 i32) global.get 0 @@ -322,7 +324,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -396,7 +398,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -415,7 +417,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat index 0289b4b5f..032e33815 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_get.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -275,7 +277,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -349,7 +351,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -368,7 +370,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat index 21d0b3485..6fc201684 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getFirst.wat @@ -183,7 +183,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -272,7 +274,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -346,7 +348,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -365,7 +367,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat index a6f7cdd19..914b2543f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_getLast.wat @@ -183,7 +183,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -272,7 +274,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -346,7 +348,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -365,7 +367,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat index 342b42f37..f4f6e54d8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_indexOf.wat @@ -22,7 +22,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -173,7 +175,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -247,7 +249,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -266,7 +268,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat index 92963ff83..740b77678 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterAdd.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -504,7 +506,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -578,7 +580,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -597,7 +599,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat index 69ab430f5..f386f204c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_iterRemove.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -302,7 +304,7 @@ call 2 local.get 0 i32.load offset=40 - free + call 5 call $teardown_test local.get 0 i32.const 48 @@ -364,7 +366,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -438,7 +440,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -457,7 +459,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat index ccfd18671..68a3aea57 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_new.wat @@ -21,7 +21,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -163,7 +165,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -237,7 +239,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -256,7 +258,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat index 50889a5c4..2c61ed331 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_remove.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -270,7 +272,7 @@ call 2 local.get 0 i32.load offset=8 - free + call 5 call $teardown_test local.get 0 i32.const 16 @@ -332,7 +334,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -406,7 +408,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -425,7 +427,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat index d9c64fdab..7f2e4f336 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAll.wat @@ -183,7 +183,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -286,7 +288,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -360,7 +362,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -379,7 +381,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat index cdeafce38..7935ec891 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeAt.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -207,7 +209,7 @@ drop local.get 0 i32.load offset=8 - free + call 5 i32.const 0 i32.load offset=1044 i32.const 2 @@ -243,7 +245,7 @@ drop local.get 0 i32.load offset=8 - free + call 5 i32.const 0 i32.load offset=1044 i32.const 0 @@ -322,7 +324,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -396,7 +398,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -415,7 +417,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat index dca459d9e..2f34f3151 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeFirst.wat @@ -184,7 +184,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -205,7 +207,7 @@ drop local.get 0 i32.load offset=8 - free + call 5 i32.const 3 i32.const 0 i32.load offset=1044 @@ -291,7 +293,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -365,7 +367,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -384,7 +386,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat index 8cd32ce75..c948d55e8 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_removeLast.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -206,7 +208,7 @@ drop local.get 0 i32.load offset=8 - free + call 5 i32.const 3 i32.const 0 i32.load offset=1044 @@ -292,7 +294,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -366,7 +368,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -385,7 +387,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat index d76188995..dacb5aec6 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_replaceAt.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -220,7 +222,7 @@ drop local.get 0 i32.load - free + call 5 i32.const 0 i32.load offset=1048 i32.const 2 @@ -296,7 +298,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -370,7 +372,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -389,7 +391,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat index 7b3d7ddac..75c83658b 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_reverse.wat @@ -22,7 +22,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -237,7 +239,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -311,7 +313,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -330,7 +332,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat index 2bd9b4f96..4e35119c1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_splice.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -329,7 +331,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -403,7 +405,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -422,7 +424,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat index 5652383c9..2e6cfd1cb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_spliceAt.wat @@ -186,7 +186,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -331,7 +333,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -405,7 +407,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -424,7 +426,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat index 9942aaf36..16be5febf 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_sublist.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -302,7 +304,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -376,7 +378,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -395,7 +397,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat index 078c74433..7fd00e8ce 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_toArray.wat @@ -185,7 +185,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -257,7 +259,7 @@ call 2 local.get 0 i32.load offset=8 - free + call 5 call $teardown_test local.get 0 i32.const 16 @@ -319,7 +321,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -393,7 +395,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -412,7 +414,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat index 047d7758a..bbe7c0735 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterAdd.wat @@ -23,7 +23,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -866,7 +868,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -940,7 +942,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -959,7 +961,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat index 0c833ec7a..9afb7e41a 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterNext.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -500,7 +502,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -574,7 +576,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -593,7 +595,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat index a94015457..6d733ae45 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterRemove.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -753,7 +755,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -827,7 +829,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -846,7 +848,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat index 2e6c2dc4e..03ad98380 100644 --- a/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat +++ b/benchmarks/pldi2026/Collection-C-normal/slist/slist_test_zipIterReplace.wat @@ -24,7 +24,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -740,7 +742,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -814,7 +816,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -833,7 +835,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat index a44a06ac9..b442ca91c 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_pop.wat @@ -16,7 +16,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -833,7 +835,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -907,7 +909,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -926,7 +928,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat index 223d561d0..a32b24462 100644 --- a/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat +++ b/benchmarks/pldi2026/Collection-C-normal/stack/stack_test_push.wat @@ -16,7 +16,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 4) (result i32) (local i32) global.get 0 @@ -697,7 +699,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -771,7 +773,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -790,7 +792,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat index 8f26c9bba..8c13481f3 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_add.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -186,7 +188,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -260,7 +262,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -279,7 +281,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat index 78007bb05..a552df011 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterNext.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -300,7 +302,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -374,7 +376,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -393,7 +395,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat index e69de2c38..c74e29062 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_iterRemove.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -215,7 +217,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -289,7 +291,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -308,7 +310,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat index a7b71a0b4..cf11f2cff 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_remove.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -179,7 +181,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -253,7 +255,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -272,7 +274,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat index eb45b9e47..26cb7ce5d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_removeAll.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -193,7 +195,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -267,7 +269,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -286,7 +288,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat index 5184be16f..8a8ff3c1d 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treeset/treeset_test_size.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -159,7 +161,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -233,7 +235,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -252,7 +254,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat index 83dc96716..4a1530595 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_add.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -196,7 +198,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -270,7 +272,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -289,7 +291,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat index 5b92e8158..a7f93cbc1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_get.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -282,7 +284,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -356,7 +358,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -375,7 +377,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat index 9acbb1fd7..447bbed27 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getFirst.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -239,7 +241,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -313,7 +315,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -332,7 +334,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat index 530c23af9..02b8cf4bb 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getGreaterThan.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -242,7 +244,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -316,7 +318,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -335,7 +337,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat index e213af8d9..0e039204e 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLast.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -239,7 +241,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -313,7 +315,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -332,7 +334,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat index 09e35d9d4..388947852 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_getLessThan.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -242,7 +244,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -316,7 +318,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -335,7 +337,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat index 8d5b5f43d..855d4e926 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterNext.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -363,7 +365,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -437,7 +439,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -456,7 +458,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat index c956d7dbf..97ec51093 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_iterRemove.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -267,7 +269,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -341,7 +343,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -360,7 +362,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat index ee4a348db..635184ca1 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_remove.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -211,7 +213,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -285,7 +287,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -304,7 +306,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat index a0b03810f..8d2dd1335 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeAll.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32) global.get 0 @@ -198,7 +200,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -272,7 +274,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -291,7 +293,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat index ce72731c4..209228b29 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeFirst.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -240,7 +242,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -314,7 +316,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -333,7 +335,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat index 9b80c7a00..64bcf05ce 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_removeLast.wat @@ -9,7 +9,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -240,7 +242,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -314,7 +316,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -333,7 +335,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add diff --git a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat index bd2721677..9b18c1e5f 100644 --- a/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat +++ b/benchmarks/pldi2026/Collection-C-normal/treetable/treetable_test_size.wat @@ -8,7 +8,9 @@ (import "i32" "symbolic" (func (;0;) (type 0))) (import "i32" "sym_assume" (func (;1;) (type 1))) (import "i32" "sym_assert" (func (;2;) (type 1))) - (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "sym" "get_sym_int32" (func (;3;) (type 0))) + (import "mem" "alloc" (func (;4;) (type 0))) + (import "mem" "free" (func (;5;) (type 2))) (func $__original_main (type 3) (result i32) (local i32 i32) global.get 0 @@ -206,7 +208,7 @@ i32.load offset=8 local.get 1 i32.load offset=12 - alloc + call 4 local.set 0 local.get 1 i32.const 16 @@ -280,7 +282,7 @@ local.get 2 i32.load offset=8 i32.mul - alloc + call 4 local.set 1 local.get 2 i32.const 16 @@ -299,7 +301,7 @@ i32.store offset=12 local.get 1 i32.load offset=12 - free + call 5 local.get 1 i32.const 16 i32.add From 5f9a65f2690f5ec7ebc00ad733a42d3d432cc10b Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 12:13:29 -0500 Subject: [PATCH 097/105] support some operations --- headers/wasm/smt_solver.hpp | 15 +++++++++++ headers/wasm/symbolic_rt.hpp | 25 ++++++++++++++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 26 ++++++++++++++++++- 3 files changed, 65 insertions(+), 1 deletion(-) diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index 8e0de42a0..cb2230541 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -114,6 +114,10 @@ inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { auto temp_bool = left < right; return z3::ite(temp_bool, one_bv, zero_bv); } + case LTU: { + auto temp_bool = z3::ult(left, right); + return z3::ite(temp_bool, one_bv, zero_bv); + } case LEQ: { auto temp_bool = left <= right; return z3::ite(temp_bool, one_bv, zero_bv); @@ -122,6 +126,17 @@ inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { auto temp_bool = left > right; return z3::ite(temp_bool, one_bv, zero_bv); } + case GTU: { + auto temp_bool = z3::ugt(left, right); + return z3::ite(temp_bool, one_bv, zero_bv); + } + case GEU: { + auto temp_bool = z3::uge(left, right); + return z3::ite(temp_bool, one_bv, zero_bv); + } + case SHR: { + return z3::lshr(left, right); + } case GEQ: { auto temp_bool = left >= right; return z3::ite(temp_bool, one_bv, zero_bv); diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index e696d7656..06e7c8b5d 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -81,9 +81,13 @@ enum Operation { EQ, // Equal NEQ, // Not equal LT, // Less than + LTU, // Unsigned less than LEQ, // Less than or equal GT, // Greater than + GTU, // Unsigned greater than GEQ, // Greater than or equal + GEU, // Unsigned greater than or equal + SHR, // Shift right B_AND, // Bitwise AND CONCAT, // Byte-level concatenation }; @@ -112,9 +116,13 @@ struct SymVal { SymVal eq(const SymVal &other) const; SymVal neq(const SymVal &other) const; SymVal lt(const SymVal &other) const; + SymVal ltu(const SymVal &other) const; SymVal le(const SymVal &other) const; SymVal gt(const SymVal &other) const; + SymVal gtu(const SymVal &other) const; SymVal ge(const SymVal &other) const; + SymVal geu(const SymVal &other) const; + SymVal shr(const SymVal &other) const; SymVal negate() const; SymVal bitwise_and(const SymVal &other) const; SymVal concat(const SymVal &other) const; @@ -209,6 +217,11 @@ inline SymVal SymVal::lt(const SymVal &other) const { return make_binary(LT, *this, other); } +inline SymVal SymVal::ltu(const SymVal &other) const { + // for now, we treat unsigned less than as signed less than + return make_binary(LTU, *this, other); +} + inline SymVal SymVal::le(const SymVal &other) const { return make_binary(LEQ, *this, other); } @@ -217,10 +230,22 @@ inline SymVal SymVal::gt(const SymVal &other) const { return make_binary(GT, *this, other); } +inline SymVal SymVal::gtu(const SymVal &other) const { + return make_binary(GTU, *this, other); +} + inline SymVal SymVal::ge(const SymVal &other) const { return make_binary(GEQ, *this, other); } +inline SymVal SymVal::geu(const SymVal &other) const { + return make_binary(GEU, *this, other); +} + +inline SymVal SymVal::shr(const SymVal &other) const { + return make_binary(SHR, *this, other); +} + inline SymVal SymVal::is_zero() const { return make_binary(EQ, *this, Concrete(I32V(0))); } diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 0b24dfde0..0f65642e6 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -616,6 +616,24 @@ trait StagedWasmEvaluator extends SAIOps { runtimeSymAssert(s) runtimeAssert(v.toInt != 0) eval(rest, kont, mkont, trail)(newCtx) + case Import("mem", "alloc", _) => + // this semantics here is not standardized in wasp, here is wasp's impl + // https://github.com/formalsec/wasp/blob/release/0.2.3/wasp/symbolic/concolic.ml#L449 + val (_, newCtx1) = ctx.pop() + val a = Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + val (_, newCtx2) = newCtx1.pop() + val b = Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + Stack.pushC(b) + val s = "Concrete".reflectCtrlWith[SymVal](Values.I32V(b.toInt)) + Stack.pushS(StagedSymbolicNum(NumType(I32Type), s)) + eval(rest, kont, mkont, trail)(newCtx1) + case Import("mem", "free", _) => + val (_, newCtx) = ctx.pop() + Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + eval(rest, kont, mkont, trail)(newCtx) case Import(m, f, _) => throw new Exception(s"Unknown import $m.$f at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } @@ -1722,7 +1740,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "i32-binary-shl", List(lhs, rhs), _) => shallow(lhs); emit(".i32_shl("); shallow(rhs); emit(")") case Node(_, "i32-binary-shr", List(lhs, rhs), _) => - shallow(lhs); emit(".i32_shr("); shallow(rhs); emit(")") + shallow(lhs); emit(".i32_shr_s("); shallow(rhs); emit(")") case Node(_, "i32-binary-and", List(lhs, rhs), _) => shallow(lhs); emit(".i32_and("); shallow(rhs); emit(")") case Node(_, "i32-relation-eq", List(lhs, rhs), _) => @@ -1777,6 +1795,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".leu("); shallow(rhs); emit(")") case Node(_, "sym-relation-lts", List(lhs, rhs), _) => shallow(lhs); emit(".lt("); shallow(rhs); emit(")") + case Node(_, "relation-ltu", List(lhs, rhs), _) => + shallow(lhs); emit(".ltu("); shallow(rhs); emit(")") case Node(_, "sym-relation-ges", List(lhs, rhs), _) => shallow(lhs); emit(".ge("); shallow(rhs); emit(")") case Node(_, "sym-relation-geu", List(lhs, rhs), _) => @@ -1787,6 +1807,10 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".neq("); shallow(rhs); emit(")") case Node(_, "sym-relation-gt", List(lhs, rhs), _) => shallow(lhs); emit(".gt("); shallow(rhs); emit(")") + case Node(_, "sym-relation-gtu", List(lhs, rhs), _) => + shallow(lhs); emit(".gtu("); shallow(rhs); emit(")") + case Node(_, "sym-binary-shr", List(lhs, rhs), _) => + shallow(lhs); emit(".shr("); shallow(rhs); emit(")") case Node(_, "num-to-int", List(num), _) => shallow(num); emit(".toInt()") case Node(_, "make-symbolic", List(num), _) => From beb8647fef38493875b35fe5cee9aee378ee072e Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 12:17:18 -0500 Subject: [PATCH 098/105] tweak --- headers/wasm/concolic_driver.hpp | 1 - headers/wasm/concrete_rt.hpp | 13 ++++++------- 2 files changed, 6 insertions(+), 8 deletions(-) diff --git a/headers/wasm/concolic_driver.hpp b/headers/wasm/concolic_driver.hpp index e26d6dbd2..29639e573 100644 --- a/headers/wasm/concolic_driver.hpp +++ b/headers/wasm/concolic_driver.hpp @@ -98,7 +98,6 @@ inline void ConcolicDriver::main_exploration_loop() { } auto &new_env = result.value().first; auto &model = result.value().second; - std::cout << "Get from model..." << std::endl << model << std::endl; // update global symbolic environment from SMT solved model SymEnv.update(std::move(new_env)); diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 753b3d63c..09d097b76 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -639,7 +639,6 @@ static std::monostate unreachable() { } static int32_t pagesize = 65536; -static int32_t page_count = 0; struct Memory_t { // TODO: We assign a SymVal to each byte in memory @@ -648,7 +647,7 @@ struct Memory_t { int page_count; Memory_t(int32_t init_page_count) - : memory(pagesize), init_page_count(init_page_count), + : memory(pagesize * init_page_count), init_page_count(init_page_count), page_count(init_page_count) {} int32_t loadInt(int32_t base, int32_t offset) { @@ -672,10 +671,6 @@ struct Memory_t { std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { int32_t addr = base + offset; -#ifdef DEBUG - std::cout << "[Debug] storing int " << value << " to memory at address " - << addr << std::endl; -#endif // Ensure we don't write out of bounds if (!(addr + 3 < memory.size())) { throw std::runtime_error("Invalid memory access " + std::to_string(addr)); @@ -684,7 +679,11 @@ struct Memory_t { memory[addr + i] = static_cast((value >> (8 * i)) & 0xFF); // Optionally, update memory[addr + i].second (SymVal) if needed } +#ifdef DEBUG + std::cout << "[Debug] storing int " << value << " to memory at address " + << addr << std::endl; std::cout << "[Debug] stored int value " << value << " to " << addr << std::endl; +#endif return std::monostate{}; } @@ -722,7 +721,7 @@ struct Memory_t { } }; -static Memory_t Memory(1); // 1 page memory +static Memory_t Memory(4); // 4 page memory struct FuncTable_t { FuncTable_t() : table(20) {} From f926137e43b74adb2cca66caebe8817094443b6b Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 12:53:01 -0500 Subject: [PATCH 099/105] a script to run wasp on btree benchmarks --- benchmarks/pldi2026/wasp_btree/run.py | 70 +++++++++++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 benchmarks/pldi2026/wasp_btree/run.py diff --git a/benchmarks/pldi2026/wasp_btree/run.py b/benchmarks/pldi2026/wasp_btree/run.py new file mode 100644 index 000000000..fb19b77d3 --- /dev/null +++ b/benchmarks/pldi2026/wasp_btree/run.py @@ -0,0 +1,70 @@ +from pathlib import Path +import subprocess +import argparse +import sys + +#!/usr/bin/env python3 +import concurrent.futures + +def run_wast(path: Path, timeout: float | None): + log_path = path.with_suffix(path.suffix + ".log") + cmd = ["wasp", str(path), "--workspace", str(path.parent / f"{path.stem}.out")] + try: + proc = subprocess.run(cmd, capture_output=True, text=True, timeout=timeout) + out = proc.stdout + err = proc.stderr + rc = proc.returncode + except subprocess.TimeoutExpired as e: + out = e.stdout or "" + err = (e.stderr or "") + f"\n[ERROR] timeout after {timeout}s" + rc = 124 + except Exception as e: + out = "" + err = f"[ERROR] failed to run wasp: {e}" + rc = 1 + + with open(log_path, "w", encoding="utf-8") as f: + f.write(f"$ {' '.join(cmd)}\n\n") + f.write("=== STDOUT ===\n") + f.write(out or "") + f.write("\n\n=== STDERR ===\n") + f.write(err or "") + + return path.name, rc + +def main(): + parser = argparse.ArgumentParser(description="Run wasp on all .wast files in the current directory.") + parser.add_argument("-j", "--jobs", type=int, default=1, help="number of parallel jobs (default 1)") + parser.add_argument("--timeout", type=float, default=None, help="per-file timeout in seconds") + args = parser.parse_args() + + cwd = Path.cwd() + wast_files = sorted([p for p in cwd.iterdir() if p.is_file() and p.suffix == ".wast"]) + if not wast_files: + print("No .wast files found in the current directory.") + return + + results = [] + if args.jobs == 1: + for p in wast_files: + results.append(run_wast(p, args.timeout)) + else: + with concurrent.futures.ThreadPoolExecutor(max_workers=args.jobs) as exe: + futures = {exe.submit(run_wast, p, args.timeout): p for p in wast_files} + for fut in concurrent.futures.as_completed(futures): + results.append(fut.result()) + + failed = [(name, rc) for (name, rc) in results if rc != 0] + for name, rc in results: + status = "OK" if rc == 0 else f"FAIL(rc={rc})" + print(f"{name}: {status}") + + if failed: + print(f"\n{len(failed)} failed. See corresponding .log files for details.") + sys.exit(1) + else: + print("\nAll runs succeeded.") + sys.exit(0) + +if __name__ == "__main__": + main() \ No newline at end of file From 0b3cfea822bfe8045e89d1bc44c69d5c338453a7 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 18:43:52 -0500 Subject: [PATCH 100/105] data section initialize --- benchmarks/wasm/data_sec.wat | 14 ++++++++++++++ headers/wasm/concrete_rt.hpp | 1 + headers/wasm/symbolic_rt.hpp | 18 ++++++++++++++++-- src/main/scala/wasm/AST.scala | 2 +- src/main/scala/wasm/Parser.scala | 6 ++++++ .../scala/wasm/StagedConcolicMiniWasm.scala | 19 +++++++++++++++++++ .../genwasym/TestStagedConcolicEval.scala | 4 ++++ 7 files changed, 61 insertions(+), 3 deletions(-) create mode 100644 benchmarks/wasm/data_sec.wat diff --git a/benchmarks/wasm/data_sec.wat b/benchmarks/wasm/data_sec.wat new file mode 100644 index 000000000..fe40aad1f --- /dev/null +++ b/benchmarks/wasm/data_sec.wat @@ -0,0 +1,14 @@ +(module + ;; define one page of memory (64 KiB) + (memory 1) + + ;; data bytes at address 0: 01 02 03 04 + (data (i32.const 0) "\01\02\03\04") + + ;; load all 4 bytes as one i32 (little-endian → 0x04030201 = 67305985) + (func (result i32) + i32.const 0 + i32.load + ) + (start 0) +) \ No newline at end of file diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 09d097b76..49622b6c1 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -733,6 +733,7 @@ struct FuncTable_t { std::to_string(index)); } if (!table[index]) { + assert(false); throw std::runtime_error("Function table entry at index " + std::to_string(index) + " is empty or invalid"); } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index 06e7c8b5d..bc5606e00 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -578,6 +578,20 @@ class SymMemory_t { static SymMemory_t SymMemory; +static std::monostate memoryInitialize(int32_t offset, + const std::string &data) { + // initialize concrete memory + for (size_t i = 0; i < data.size(); ++i) { + Memory.storeInt(offset, i, static_cast(data[i])); + } + // initialize symbolic memory + for (size_t i = 0; i < data.size(); ++i) { + SymMemory.storeSym(offset + i, 0, + Concrete(I32V(static_cast(data[i])))); + } + return {}; +} + // A snapshot of the symbolic state and execution context (control) class Snapshot_t { public: @@ -940,7 +954,7 @@ inline std::monostate NodeBox::fillNotToExploreNode() { } inline std::monostate NodeBox::fillFinishedNode() { - if (this->isUnexplored()) { + if (this->isUnexplored()) { node = std::make_unique(); } else { assert(dynamic_cast(node.get()) != nullptr); @@ -1061,7 +1075,7 @@ inline int Snapshot_t::cost_of_snapshot() { auto cost_of_memory_copy = SymMemory.cost_of_copy(); // The speed ratio between symbolic expression instantiation and WebAssembly // instruction execution, given by benchmark results - auto ratio = 5.336; + auto ratio = 2.5; return ratio * (cost_of_stack_copy + cost_of_frame_copy + cost_of_memory_copy); } diff --git a/src/main/scala/wasm/AST.scala b/src/main/scala/wasm/AST.scala index 2aad8052c..60cf0c4fb 100644 --- a/src/main/scala/wasm/AST.scala +++ b/src/main/scala/wasm/AST.scala @@ -15,7 +15,7 @@ case class Table(id: Option[String], f: TableField) extends Definition case class Memory(id: Option[String], f: MemoryField) extends Definition case class Global(id: Option[String], f: GlobalField) extends Definition case class Elem(id: Option[Int], offset: List[Instr], elemList: ElemList) extends Definition -case class Data(id: Option[String], value: String) extends Definition +case class Data(id: Option[String], offset: Instr, value: String) extends Definition case class Start(id: Int) extends Definition case class Import(mod: String, name: String, desc: ImportDesc) extends Definition with Callable case class Export(name: String, desc: ExportDesc) extends Definition diff --git a/src/main/scala/wasm/Parser.scala b/src/main/scala/wasm/Parser.scala index 5f03b5b1d..27b215fab 100644 --- a/src/main/scala/wasm/Parser.scala +++ b/src/main/scala/wasm/Parser.scala @@ -170,6 +170,12 @@ class GSWasmVisitor extends WatParserBaseVisitor[WIR] { f } + override def visitData(ctx: DataContext): Data = { + val instr = visit(ctx.instr()).asInstanceOf[Instr] + val str = ctx.STRING_.asScala.toList.map(_.getText.substring(1).dropRight(1)).mkString + Data(None, instr, str) + } + override def visitElem(ctx: ElemContext): Elem = { val offsetInstrs = List(visit(ctx.instr()).asInstanceOf[Instr]) val funcs = ctx.idx().asScala.map(getVar(_)).map { id => diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 0f65642e6..87871df9d 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -756,6 +756,7 @@ trait StagedWasmEvaluator extends SAIOps { // resetStacks() // Don't manually reset the global states (like stack), manage them in the driver initGlobals(module.globals) initTable(module) + initMemory() Frames.pushFrameC(locals) Frames.pushFrameS(locals) eval(instrs, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, locals)) @@ -964,6 +965,22 @@ trait StagedWasmEvaluator extends SAIOps { } } + def initMemory(): Rep[Unit] = { + for (definition <- module.defs) { + definition match { + case Data(_, offsetInstr, bytes) => + val haltK: Rep[Unit] => Rep[Unit] = (_) => { } + val mkont: Rep[MCont[Unit]] = makeInitMCont(topFun(haltK)) + eval(offsetInstr::Nil, (_: Context) => forwardKont, mkont, ((_: Context) => forwardKont)::Nil)(Context(Nil, Nil)) + val offsetC = Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + Predef.printf("Initializing memory of %s\n", bytes) + "memory-initialize".reflectCtrlWith[Unit](offsetC.toInt, bytes) + case _ => () + } + } + } + // call unreachable def unreachable(): Rep[Unit] = { "unreachable".reflectCtrlWith[Unit]() @@ -1857,6 +1874,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { emit("FuncTable.read("); shallow(funcIndex); emit(")") case Node(_, "tree-move-cursor-call-indirect-index", List(index), _) => emit("ExploreTree.moveCursorIndirect("); shallow(index); emit(")") + case Node(_, "memory-initialize", List(offset, str), _) => + emit("memoryInitialize("); shallow(offset); emit(", "); shallow(str); emit(")") case Node(_, "dummy", _, _) => emit("std::monostate()") case Node(_, "dummy-op", _, _) => emit("std::monostate()") case Node(_, "no-op", _, _) => diff --git a/src/test/scala/genwasym/TestStagedConcolicEval.scala b/src/test/scala/genwasym/TestStagedConcolicEval.scala index 53ed775e8..2a243825f 100644 --- a/src/test/scala/genwasym/TestStagedConcolicEval.scala +++ b/src/test/scala/genwasym/TestStagedConcolicEval.scala @@ -194,6 +194,10 @@ class TestStagedConcolicEval extends FunSuite { testFileConcreteCpp("./benchmarks/wasm/call_indirect_test.wat", expect=Some(List(42))) } + test("data-section-concrete") { + testFileConcreteCpp("./benchmarks/wasm/data_sec.wat", expect=Some(List(67305985))) + } + // test("diverge") { // testFileConcolicCpp("./benchmarks/wasm/diverge.wat", Some("main")) // } From a4cd4a56e532b2569b0c0a401e44e5acd5bb6fef Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Tue, 11 Nov 2025 20:45:22 -0500 Subject: [PATCH 101/105] revert something --- headers/wasm/concrete_rt.hpp | 75 +++++++------------ headers/wasm/symbolic_rt.hpp | 44 +---------- .../scala/wasm/StagedConcolicMiniWasm.scala | 60 +++++++++++++-- 3 files changed, 82 insertions(+), 97 deletions(-) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 49622b6c1..532acdf7d 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -540,7 +540,6 @@ class Stack_t { static Stack_t Stack; const int FRAME_SIZE = 1024 * 8; - class Frames_t { public: Frames_t() : count(0), stack_ptr(new Num[FRAME_SIZE]) { @@ -553,38 +552,22 @@ class Frames_t { std::monostate popFrame(std::int32_t size) { assert(size >= 0); - assert(size == count - current_base); count -= size; - current_base = old_frame_bases.back(); - old_frame_bases.pop_back(); return std::monostate{}; } Num get(std::int32_t index) { Profile.step(StepProfileKind::GET); - auto ret = stack_ptr[current_base + index]; + auto ret = stack_ptr[count - 1 - index]; return ret; } void set(std::int32_t index, Num num) { Profile.step(StepProfileKind::SET); - stack_ptr[current_base + index] = num; + stack_ptr[count - 1 - index] = num; } void pushFrame(std::int32_t size) { - assert(size >= 0); - assert(count + size <= FRAME_SIZE); - - old_frame_bases.push_back(current_base); - current_base = count; - count += size; - // Zero-initialize the new stack frames. - for (std::int32_t i = 0; i < size; ++i) { - stack_ptr[count - 1 - i] = Num(0); - } - } - - void extendFrame(std::int32_t size) { assert(size >= 0); count += size; // Zero-initialize the new stack frames. @@ -593,10 +576,7 @@ class Frames_t { } } - void reset() { - count = 0; - current_base = 0; - } + void reset() { count = 0; } size_t size() const { return count; } @@ -610,20 +590,9 @@ class Frames_t { count = new_size; } - void resize_old_frames_size(int32_t new_size) { - assert(new_size >= 0); - old_frame_bases.resize(new_size); - } - - void set_old_frame_base(int32_t index, int32_t value) { - assert(index >= 0 && index < old_frame_bases.size()); - old_frame_bases[index] = value; - } - +private: int32_t count; Num *stack_ptr; - int32_t current_base; - std::vector old_frame_bases; }; static Frames_t Frames; @@ -638,19 +607,26 @@ static std::monostate unreachable() { throw std::runtime_error("Unreachable code reached"); } +static const int PRE_ALLOC_PAGES = 20; static int32_t pagesize = 65536; +static int32_t page_count = 0; struct Memory_t { // TODO: We assign a SymVal to each byte in memory std::vector memory; int init_page_count; int page_count; + int allocated_pages; Memory_t(int32_t init_page_count) - : memory(pagesize * init_page_count), init_page_count(init_page_count), - page_count(init_page_count) {} + : memory(PRE_ALLOC_PAGES * pagesize), init_page_count(init_page_count), + page_count(init_page_count), allocated_pages(PRE_ALLOC_PAGES) {} int32_t loadInt(int32_t base, int32_t offset) { +#ifdef DEBUG + std::cout << "[Debug] loading int from memory at address: " + << (base + offset) << std::endl; +#endif // just load a 4-byte integer from memory of the vector int32_t addr = base + offset; if (!(addr + 3 < memory.size())) { @@ -661,16 +637,15 @@ struct Memory_t { for (int i = 0; i < 4; ++i) { result |= static_cast(memory[addr + i]) << (8 * i); } -#ifdef DEBUG - std::cout << "[Debug] loading int from memory at address: " - << (base + offset) << std::endl; - std::cout << "[Debug] loaded int value " << result << " from " << addr << std::endl; -#endif return result; } std::monostate storeInt(int32_t base, int32_t offset, int32_t value) { int32_t addr = base + offset; +#ifdef DEBUG + std::cout << "[Debug] storing int " << value << " to memory at address " + << addr << std::endl; +#endif // Ensure we don't write out of bounds if (!(addr + 3 < memory.size())) { throw std::runtime_error("Invalid memory access " + std::to_string(addr)); @@ -679,11 +654,6 @@ struct Memory_t { memory[addr + i] = static_cast((value >> (8 * i)) & 0xFF); // Optionally, update memory[addr + i].second (SymVal) if needed } -#ifdef DEBUG - std::cout << "[Debug] storing int " << value << " to memory at address " - << addr << std::endl; - std::cout << "[Debug] stored int value " << value << " to " << addr << std::endl; -#endif return std::monostate{}; } @@ -701,11 +671,15 @@ struct Memory_t { return page_count * pagesize; } + if (page_count + delta < allocated_pages) { + page_count += delta; + return page_count * pagesize; + } + try { + assert(false && "Use pre-allocated memory, should not reach here"); memory.resize(memory.size() + delta * pagesize); - for (int i = 0; i < delta * pagesize; ++i) { - memory[page_count * pagesize + i] = 0; - } + auto old_page_count = page_count; page_count += delta; return memory.size(); } catch (const std::bad_alloc &e) { @@ -715,6 +689,7 @@ struct Memory_t { void reset() { page_count = init_page_count; + allocated_pages = PRE_ALLOC_PAGES; for (int i = 0; i < memory.size() && i < page_count * pagesize; ++i) { memory[i] = 0; } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index bc5606e00..a067b6e24 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -380,60 +380,37 @@ class SymFrames_t { void pushFrame(int size) { // Push a new frame with the given size #ifdef USE_IMM - old_frame_bases.push_back(current_base); - current_base = stack.size(); for (int i = 0; i < size; ++i) { stack.push_back(SymVal()); } #else - old_frame_bases.push_back(current_base); - current_base = stack.size(); stack.resize(size + stack.size()); #endif } - - void extendFrame(int size) { - // Extend the current frame with the given size -#ifdef USE_IMM - for (int i = 0; i < size; ++i) { - stack.push_back(SymVal()); - } -#else - stack.resize(size + stack.size()); -#endif - } - std::monostate popFrame(int size) { // Pop the frame of the given size #ifdef USE_IMM - assert(size == stack.size() - current_base); stack.take(stack.size() - size); - current_base = old_frame_bases.end()[-1]; - old_frame_bases.take(old_frame_bases.size() - 1); #else stack.resize(stack.size() - size); - current_base = old_frame_bases.back(); - old_frame_bases.pop_back(); #endif return std::monostate(); } SymVal get(int index) { // Get the symbolic value at the given frame index - assert(index >= 0 && index < size() - current_base); - auto res = stack[current_base + index]; + auto res = stack[stack.size() - 1 - index]; return res; } void set(int index, SymVal val) { // Set the symbolic value at the given index assert(val.symptr != nullptr); - assert(index >= 0 && index < size() - current_base); #ifdef USE_IMM - stack.set(current_base + index, val); + stack.set(stack.size() - 1 - index, val); #else - stack[current_base + index] = val; + stack[stack.size() - 1 - index] = val; #endif } @@ -442,12 +419,8 @@ class SymFrames_t { #ifdef USE_IMM stack = immer::vector_transient(); - old_frame_bases = immer::vector_transient(); - current_base = 0; #else stack.clear(); - old_frame_bases.clear(); - current_base = 0; #endif } @@ -463,14 +436,11 @@ class SymFrames_t { return cost; } +private: #ifdef USE_IMM immer::vector_transient stack; - immer::vector_transient old_frame_bases; - int32_t current_base = 0; #else std::vector stack; - std::vector old_frame_bases; - int32_t current_base = 0; #endif }; @@ -1603,12 +1573,6 @@ static void resume_conc_frames_by_model(const SymFrames_t &sym_frame, auto conc = res.value; frames.set_from_front(i, conc); } - frames.resize_old_frames_size(sym_frame.old_frame_bases.size()); - for (size_t i = 0; i < sym_frame.old_frame_bases.size(); ++i) { - auto base = sym_frame.old_frame_bases[i]; - frames.set_old_frame_base(i, base); - } - frames.current_base = sym_frame.current_base; } static void resume_conc_memory(const SymMemory_t &sym_memory, Memory_t &memory, diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index 87871df9d..f5475e802 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -214,6 +214,25 @@ trait StagedWasmEvaluator extends SAIOps { Stack.pushS(Frames.getS(i)) val newCtx = ctx.push(ctx.frameTypes(i)) eval(rest, kont, mkont, trail)(newCtx) + case Select(ty) => + val (ty1, newCtx1) = ctx.pop() + val cond = Stack.popC(ty1) + val condSym = Stack.popS(ty1) + val (ty2, newCtx2) = newCtx1.pop() + val falseVal = Stack.popC(ty2) + val falseSym = Stack.popS(ty2) + val (ty3, newCtx3) = newCtx2.pop() + val trueVal = Stack.popC(ty3) + val trueSym = Stack.popS(ty3) + if (cond.toInt != 0) { + Stack.pushC(trueVal) + Stack.pushS(trueSym) + } else { + Stack.pushC(falseVal) + Stack.pushS(falseSym) + } + val newCtx4 = newCtx3.push(ty2) + eval(rest, kont, mkont, trail)(newCtx4) case LocalSet(i) => val (ty, newCtx) = ctx.pop() val num = Stack.popC(ty) @@ -287,7 +306,7 @@ trait StagedWasmEvaluator extends SAIOps { val s = Stack.popS(ty) Stack.pushC(evalTestOpC(op, v)) Stack.pushS(evalTestOpS(op, s)) - val newCtx2 = newCtx1.push(v.tipe) + val newCtx2 = newCtx1.push(NumType(I32Type)) eval(rest, kont, mkont, trail)(newCtx2) case Unary(op) => val (ty, newCtx1) = ctx.pop() @@ -472,6 +491,8 @@ trait StagedWasmEvaluator extends SAIOps { evalCallIndirect(rest, kont, mkont, trail, functy.asInstanceOf[FuncType]) case _ => val todo = "todo-op".reflectCtrlWith[Unit]() + Predef.println(s"[WARNING] Encountered unimplemented instruction $inst, treat it as NOP") + Predef.assert(false, s"Unimplemented instruction $inst") eval(rest, kont, mkont, trail) } } @@ -527,12 +548,8 @@ trait StagedWasmEvaluator extends SAIOps { val offset = ctx.stackTypes.size - ty.out.size Stack.shiftC(offset, ty.out.size) Stack.shiftS(offset, ty.out.size) - Frames.popFrameC(inps.size + locals.size) - Frames.popFrameS(inps.size + locals.size) mk.enter() }) - Frames.extendFrameC(locals.size) - Frames.extendFrameS(locals.size) eval(body, retK _, mk, retK _::Nil)(Context(Nil, inps ++ locals)) }) compileCache(funcIndex) = func @@ -559,11 +576,13 @@ trait StagedWasmEvaluator extends SAIOps { // (more or less like `return`) val restK: Rep[Cont[Unit]] = topFun((mk: Rep[MCont[Unit]]) => { info(s"Exiting the function at $funcIndex, stackSize =", Stack.size) + Frames.popFrameC(ty.inps.size + bodyLocals.size) + Frames.popFrameS(ty.inps.size + bodyLocals.size) eval(rest, kont, mk, trail)(newCtx.copy(stackTypes = ty.out.reverse ++ ctx.stackTypes.drop(ty.inps.size))) }) val newMKont: Rep[MCont[Unit]] = mkont.prependCont(restK) - Frames.pushFrameC(ty.inps) - Frames.pushFrameS(ty.inps) + Frames.pushFrameC(ty.inps ++ bodyLocals) + Frames.pushFrameS(ty.inps ++ bodyLocals) Frames.putAllC(argsC) Frames.putAllS(argsS) callee(newMKont) @@ -634,6 +653,12 @@ trait StagedWasmEvaluator extends SAIOps { Stack.popC(NumType(I32Type)) Stack.popS(NumType(I32Type)) eval(rest, kont, mkont, trail)(newCtx) + case Import("env", "proc_exit", _) => + val (_, newCtx) = ctx.pop() + val code = Stack.popC(NumType(I32Type)) + Stack.popS(NumType(I32Type)) + info(s"Program exiting") + eval(rest, kont, mkont, trail)(newCtx) case Import(m, f, _) => throw new Exception(s"Unknown import $m.$f at $funcIndex") case _ => throw new Exception(s"Definition at $funcIndex is not callable") } @@ -672,6 +697,7 @@ trait StagedWasmEvaluator extends SAIOps { case DivS(_) => v1 divs v2 case DivU(_) => v1 divu v2 case Div(_) => v1 div v2 + case Xor(_) => v1 xor v2 case _ => throw new Exception(s"Unknown binary operation $op") } @@ -687,6 +713,7 @@ trait StagedWasmEvaluator extends SAIOps { case DivS(_) => v1 divs v2 case DivU(_) => v1 divu v2 case Div(_) => v1 div v2 + case Xor(_) => v1 xor v2 case _ => throw new Exception(s"Unknown binary operation $op") } @@ -745,6 +772,7 @@ trait StagedWasmEvaluator extends SAIOps { case Start(id) => Some(id) case _ => None } + Predef.printf("module defs = %s", module.defs) val startId = startIds.headOption.getOrElse { throw new Exception("No start function") } module.funcs(startId) match { case FuncDef(_, body@FuncBodyDef(_,_,_,_)) => body @@ -1164,6 +1192,13 @@ trait StagedWasmEvaluator extends SAIOps { } } + def xor(rhs: StagedConcreteNum): StagedConcreteNum = { + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedConcreteNum(NumType(I32Type), "i32-binary-xor".reflectCtrlWith[Num](num.i, rhs.i)) + } + } + def <<(rhs: StagedConcreteNum): StagedConcreteNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => @@ -1434,6 +1469,13 @@ trait StagedWasmEvaluator extends SAIOps { } } + def xor(rhs: StagedSymbolicNum): StagedSymbolicNum = { + (num.tipe, rhs.tipe) match { + case (NumType(I32Type), NumType(I32Type)) => + StagedSymbolicNum(NumType(I32Type), "sym-binary-xor".reflectCtrlWith[SymVal](num.s, rhs.s)) + } + } + def <<(rhs: StagedSymbolicNum): StagedSymbolicNum = { (num.tipe, rhs.tipe) match { case (NumType(I32Type), NumType(I32Type)) => @@ -1780,6 +1822,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".i32_ge_s("); shallow(rhs); emit(")") case Node(_, "i32-relation-geu", List(lhs, rhs), _) => shallow(lhs); emit(".i32_ge_u("); shallow(rhs); emit(")") + case Node(_, "i32-binary-xor", List(lhs, rhs), _) => + shallow(lhs); emit(".i32_xor("); shallow(rhs); emit(")") case Node(_, "f32-binary-add", List(lhs, rhs), _) => shallow(lhs); emit(".f32_add("); shallow(rhs); emit(")") case Node(_, "f32-binary-sub", List(lhs, rhs), _) => @@ -1812,6 +1856,8 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { shallow(lhs); emit(".leu("); shallow(rhs); emit(")") case Node(_, "sym-relation-lts", List(lhs, rhs), _) => shallow(lhs); emit(".lt("); shallow(rhs); emit(")") + case Node(_, "sym-binary-xor", List(lhs, rhs), _) => + shallow(lhs); emit(".xor("); shallow(rhs); emit(")") case Node(_, "relation-ltu", List(lhs, rhs), _) => shallow(lhs); emit(".ltu("); shallow(rhs); emit(")") case Node(_, "sym-relation-ges", List(lhs, rhs), _) => From c880bd01a8f1c8df5269f18c8b7d87db22b3cfa7 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 12 Nov 2025 04:01:42 -0500 Subject: [PATCH 102/105] more operations --- headers/wasm/concrete_rt.hpp | 8 ++++++++ headers/wasm/smt_solver.hpp | 3 +++ headers/wasm/symbolic_rt.hpp | 7 +++++++ 3 files changed, 18 insertions(+) diff --git a/headers/wasm/concrete_rt.hpp b/headers/wasm/concrete_rt.hpp index 532acdf7d..9889db289 100644 --- a/headers/wasm/concrete_rt.hpp +++ b/headers/wasm/concrete_rt.hpp @@ -196,6 +196,14 @@ struct Num { return res; } + // i32.xor (Bitwise XOR) + inline Num i32_xor(const Num &other) const { + uint32_t result_u = this->toUInt() ^ other.toUInt(); + Num res(static_cast(result_u)); + debug_print("i32.xor", *this, other, res); + return res; + } + // f32 helpers: interpret low 32 bits of value as IEEE-754 float static inline float f32_from_bits(uint32_t bits) { union { diff --git a/headers/wasm/smt_solver.hpp b/headers/wasm/smt_solver.hpp index cb2230541..0dc09f127 100644 --- a/headers/wasm/smt_solver.hpp +++ b/headers/wasm/smt_solver.hpp @@ -156,6 +156,9 @@ inline z3::expr Solver::build_z3_expr_aux(SymVal &sym_val) { case B_AND: { return left & right; } + case B_XOR: { + return left ^ right; + } case CONCAT: { return z3::concat(left, right); } diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index a067b6e24..a07e2f6cb 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -89,6 +89,7 @@ enum Operation { GEU, // Unsigned greater than or equal SHR, // Shift right B_AND, // Bitwise AND + B_XOR, // Bitwise XOR CONCAT, // Byte-level concatenation }; static MemBookKeeper SymBookKeeper; @@ -125,6 +126,7 @@ struct SymVal { SymVal shr(const SymVal &other) const; SymVal negate() const; SymVal bitwise_and(const SymVal &other) const; + SymVal bitwise_xor(const SymVal &other) const; SymVal concat(const SymVal &other) const; SymVal extract(int high, int low) const; // TODO: add bitwise operations, and use the underlying bitvector theory @@ -266,6 +268,11 @@ inline SymVal SymVal::extract(int high, int low) const { inline SymVal SymVal::bitwise_and(const SymVal &other) const { return make_binary(B_AND, *this, other); } + +inline SymVal SymVal::bitwise_xor(const SymVal &other) const { + return make_binary(B_XOR, *this, other); +} + inline SymVal SymVal::make_binary(Operation op, const SymVal &lhs, const SymVal &rhs) { assert(lhs.symptr != nullptr && rhs.symptr != nullptr); From a4975978f62b9848168baabcc03e9a03f69fe372 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Wed, 12 Nov 2025 12:19:23 -0500 Subject: [PATCH 103/105] try not to build symbolic expressions when all operands are concrete --- headers/wasm/symbolic_rt.hpp | 6 + .../scala/wasm/StagedConcolicMiniWasm.scala | 109 +++++++++++------- 2 files changed, 75 insertions(+), 40 deletions(-) diff --git a/headers/wasm/symbolic_rt.hpp b/headers/wasm/symbolic_rt.hpp index a07e2f6cb..b47c0e657 100644 --- a/headers/wasm/symbolic_rt.hpp +++ b/headers/wasm/symbolic_rt.hpp @@ -303,6 +303,12 @@ inline bool SymVal::is_concrete() const { return dynamic_cast(symptr.get()) != nullptr; } +template inline bool allConcrete(const Args &...args) { + static_assert((std::is_same_v && ...), + "all_concrete only accepts SymVal arguments"); + return (... && args.is_concrete()); +} + class Snapshot_t; class SymStack_t { diff --git a/src/main/scala/wasm/StagedConcolicMiniWasm.scala b/src/main/scala/wasm/StagedConcolicMiniWasm.scala index f5475e802..0d0de8ec4 100644 --- a/src/main/scala/wasm/StagedConcolicMiniWasm.scala +++ b/src/main/scala/wasm/StagedConcolicMiniWasm.scala @@ -57,7 +57,11 @@ object Counter { trait StagedWasmEvaluator extends SAIOps { def module: ModuleInstance - case class StagedConcreteNum(tipe: ValueType, i: Rep[Num]) + case class StagedConcreteNum(tipe: ValueType, i: Rep[Num]) { + def toStagedSymbolicNum: StagedSymbolicNum = { + StagedSymbolicNum(tipe, "Concrete".reflectCtrlWith[SymVal](i)) + } + } case class StagedSymbolicNum(tipe: ValueType, s: Rep[SymVal]) @@ -314,7 +318,7 @@ trait StagedWasmEvaluator extends SAIOps { val s = Stack.popS(ty) val res = evalUnaryOpC(op, v) Stack.pushC(res) - Stack.pushS(evalUnaryOpS(op, s)) + Stack.pushS(evalUnaryOpS(op, s, res)) val newCtx2 = newCtx1.push(res.tipe) eval(rest, kont, mkont, trail)(newCtx2) case Binary(op) => @@ -326,7 +330,7 @@ trait StagedWasmEvaluator extends SAIOps { val s1 = Stack.popS(ty1) val res = evalBinOpC(op, v1, v2) Stack.pushC(res) - Stack.pushS(evalBinOpS(op, s1, s2)) + Stack.pushS(evalBinOpS(op, s1, s2, res)) val newCtx3 = newCtx2.push(res.tipe) eval(rest, kont, mkont, trail)(newCtx3) case Compare(op) => @@ -338,7 +342,7 @@ trait StagedWasmEvaluator extends SAIOps { val s1 = Stack.popS(ty1) val res = evalRelOpC(op, v1, v2) Stack.pushC(res) - Stack.pushS(evalRelOpS(op, s1, s2)) + Stack.pushS(evalRelOpS(op, s1, s2, res)) val newCtx3 = newCtx2.push(res.tipe) eval(rest, kont, mkont, trail)(newCtx3) case WasmBlock(ty, inner) => @@ -679,11 +683,18 @@ trait StagedWasmEvaluator extends SAIOps { case _ => ??? } - def evalUnaryOpS(op: UnaryOp, value: StagedSymbolicNum): StagedSymbolicNum = op match { - case Clz(_) => value.clz() - case Ctz(_) => value.ctz() - case Popcnt(_) => value.popcnt() - case _ => ??? + def evalUnaryOpS(op: UnaryOp, value: StagedSymbolicNum, c: StagedConcreteNum): StagedSymbolicNum = { + val res = if (allConcrete(value)) { + c.toStagedSymbolicNum.s + } else { + (op match { + case Clz(_) => value.clz() + case Ctz(_) => value.ctz() + case Popcnt(_) => value.popcnt() + case _ => throw new Exception(s"Unknown unary operation $op") + }).s + } + StagedSymbolicNum(c.tipe, res) } def evalBinOpC(op: BinOp, v1: StagedConcreteNum, v2: StagedConcreteNum): StagedConcreteNum = op match { @@ -702,20 +713,27 @@ trait StagedWasmEvaluator extends SAIOps { throw new Exception(s"Unknown binary operation $op") } - def evalBinOpS(op: BinOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum): StagedSymbolicNum = op match { - case Add(_) => v1 + v2 - case Mul(_) => v1 * v2 - case Sub(_) => v1 - v2 - case Shl(_) => v1 << v2 - // case ShrS(_) => v1 >> v2 // TODO: signed shift right - case ShrU(_) => v1 >> v2 - case And(_) => v1 & v2 - case DivS(_) => v1 divs v2 - case DivU(_) => v1 divu v2 - case Div(_) => v1 div v2 - case Xor(_) => v1 xor v2 - case _ => - throw new Exception(s"Unknown binary operation $op") + def evalBinOpS(op: BinOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum, c: StagedConcreteNum): StagedSymbolicNum = { + val res = if (allConcrete(v1, v2)) { + c.toStagedSymbolicNum.s + } else { + (op match { + case Add(_) => v1 + v2 + case Mul(_) => v1 * v2 + case Sub(_) => v1 - v2 + case Shl(_) => v1 << v2 + // case ShrS(_) => v1 >> v2 // TODO: signed shift right + case ShrU(_) => v1 >> v2 + case And(_) => v1 & v2 + case DivS(_) => v1 divs v2 + case DivU(_) => v1 divu v2 + case Div(_) => v1 div v2 + case Xor(_) => v1 xor v2 + case _ => + throw new Exception(s"Unknown binary operation $op") + }).s + } + StagedSymbolicNum(c.tipe, res) } def evalRelOpC(op: RelOp, v1: StagedConcreteNum, v2: StagedConcreteNum): StagedConcreteNum = op match { @@ -736,22 +754,29 @@ trait StagedWasmEvaluator extends SAIOps { case _ => ??? } - def evalRelOpS(op: RelOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum): StagedSymbolicNum = op match { - case Eq(_) => v1 numEq v2 - case Ne(_) => v1 numNe v2 - case LtS(_) => v1 < v2 - case LtU(_) => v1 ltu v2 - case GtS(_) => v1 > v2 - case GtU(_) => v1 gtu v2 - case LeS(_) => v1 <= v2 - case LeU(_) => v1 leu v2 - case GeS(_) => v1 >= v2 - case GeU(_) => v1 geu v2 - case Lt(_) => v1 lt v2 - case Le(_) => v1 le v2 - case Gt(_) => v1 gt v2 - case Ge(_) => v1 ge v2 - case _ => ??? + def evalRelOpS(op: RelOp, v1: StagedSymbolicNum, v2: StagedSymbolicNum, c: StagedConcreteNum): StagedSymbolicNum = { + val res = if (allConcrete(v1, v2)) { + c.toStagedSymbolicNum.s + } else { + (op match { + case Eq(_) => v1 numEq v2 + case Ne(_) => v1 numNe v2 + case LtS(_) => v1 < v2 + case LtU(_) => v1 ltu v2 + case GtS(_) => v1 > v2 + case GtU(_) => v1 gtu v2 + case LeS(_) => v1 <= v2 + case LeU(_) => v1 leu v2 + case GeS(_) => v1 >= v2 + case GeU(_) => v1 geu v2 + case Lt(_) => v1 lt v2 + case Le(_) => v1 le v2 + case Gt(_) => v1 gt v2 + case Ge(_) => v1 ge v2 + case _ => throw new Exception(s"Unknown relational operation $op") + }).s + } + StagedSymbolicNum(c.tipe, res) } def evalTop(mkont: Rep[MCont[Unit]], main: Option[String]): Rep[Unit] = { @@ -1009,6 +1034,10 @@ trait StagedWasmEvaluator extends SAIOps { } } + def allConcrete(syms: StagedSymbolicNum*): Rep[Boolean] = { + "allConcrete".reflectCtrlWith[Boolean](syms.map(_.s): _*) + } + // call unreachable def unreachable(): Rep[Unit] = { "unreachable".reflectCtrlWith[Unit]() @@ -1857,7 +1886,7 @@ trait StagedWasmCppGen extends CGenBase with CppSAICodeGenBase { case Node(_, "sym-relation-lts", List(lhs, rhs), _) => shallow(lhs); emit(".lt("); shallow(rhs); emit(")") case Node(_, "sym-binary-xor", List(lhs, rhs), _) => - shallow(lhs); emit(".xor("); shallow(rhs); emit(")") + shallow(lhs); emit(".bitwise_xor("); shallow(rhs); emit(")") case Node(_, "relation-ltu", List(lhs, rhs), _) => shallow(lhs); emit(".ltu("); shallow(rhs); emit(")") case Node(_, "sym-relation-ges", List(lhs, rhs), _) => From 7c3878ac5cfee8f66d80b44e35a7659343a616de Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 13 Nov 2025 01:23:09 -0500 Subject: [PATCH 104/105] a crafted benchmark --- benchmarks/pldi2026/crafted/parse_expr3.wat | 191 ++++++++++++++++++++ 1 file changed, 191 insertions(+) create mode 100644 benchmarks/pldi2026/crafted/parse_expr3.wat diff --git a/benchmarks/pldi2026/crafted/parse_expr3.wat b/benchmarks/pldi2026/crafted/parse_expr3.wat new file mode 100644 index 000000000..fba5ee858 --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr3.wat @@ -0,0 +1,191 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x+133*11*x+247*x+323+60*x+100*x+140*11*x+260*x+340+3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x*x*x+25*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x\00")) From 5f97900b8ec3ef0900cbebd26644464220acede9 Mon Sep 17 00:00:00 2001 From: butterunderflow Date: Thu, 13 Nov 2025 12:23:23 -0500 Subject: [PATCH 105/105] snapshot benchmark --- .../pldi2026/crafted/parse_expr150-16.wat | 221 ++++++++++++++++ .../pldi2026/crafted/parse_expr150-8.wat | 181 +++++++++++++ .../pldi2026/crafted/parse_expr160-16.wat | 216 ++++++++++++++++ .../pldi2026/crafted/parse_expr160-8.wat | 176 +++++++++++++ .../pldi2026/crafted/parse_expr190-16.wat | 208 +++++++++++++++ .../pldi2026/crafted/parse_expr190-8.wat | 181 +++++++++++++ .../pldi2026/crafted/parse_expr220-16.wat | 226 ++++++++++++++++ .../pldi2026/crafted/parse_expr220-8.wat | 182 +++++++++++++ .../pldi2026/crafted/parse_expr260-16.wat | 241 ++++++++++++++++++ .../pldi2026/crafted/parse_expr260-8.wat | 181 +++++++++++++ 10 files changed, 2013 insertions(+) create mode 100644 benchmarks/pldi2026/crafted/parse_expr150-16.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr150-8.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr160-16.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr160-8.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr190-16.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr190-8.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr220-16.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr220-8.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr260-16.wat create mode 100644 benchmarks/pldi2026/crafted/parse_expr260-8.wat diff --git a/benchmarks/pldi2026/crafted/parse_expr150-16.wat b/benchmarks/pldi2026/crafted/parse_expr150-16.wat new file mode 100644 index 000000000..6c6be2b5b --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr150-16.wat @@ -0,0 +1,221 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 9 + i32.add + if + end + local.get 0 + i32.const 10 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + local.get 0 + i32.const 12 + i32.add + if + end + local.get 0 + i32.const 13 + i32.add + if + end + local.get 0 + i32.const 13 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+1\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr150-8.wat b/benchmarks/pldi2026/crafted/parse_expr150-8.wat new file mode 100644 index 000000000..3050a7652 --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr150-8.wat @@ -0,0 +1,181 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+1\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr160-16.wat b/benchmarks/pldi2026/crafted/parse_expr160-16.wat new file mode 100644 index 000000000..41e334ea2 --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr160-16.wat @@ -0,0 +1,216 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 9 + i32.add + if + end + local.get 0 + i32.const 10 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + local.get 0 + i32.const 12 + i32.add + if + end + local.get 0 + i32.const 13 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+42*x+70*x+98\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr160-8.wat b/benchmarks/pldi2026/crafted/parse_expr160-8.wat new file mode 100644 index 000000000..42496e1ad --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr160-8.wat @@ -0,0 +1,176 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+42*x+70*x+98\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr190-16.wat b/benchmarks/pldi2026/crafted/parse_expr190-16.wat new file mode 100644 index 000000000..0ca50dc9c --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr190-16.wat @@ -0,0 +1,208 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 9 + i32.add + if + end + local.get 0 + i32.const 10 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + + + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr190-8.wat b/benchmarks/pldi2026/crafted/parse_expr190-8.wat new file mode 100644 index 000000000..cd078ef4f --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr190-8.wat @@ -0,0 +1,181 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr220-16.wat b/benchmarks/pldi2026/crafted/parse_expr220-16.wat new file mode 100644 index 000000000..e33b8548c --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr220-16.wat @@ -0,0 +1,226 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 9 + i32.add + if + end + local.get 0 + i32.const 10 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + local.get 0 + i32.const 12 + i32.add + if + end + local.get 0 + i32.const 13 + i32.add + if + end + local.get 0 + i32.const 14 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+10+x+x+3+8\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x+133*11*x+247*x+323+60*x+100*x+140*11*x+260*x+340+3*x+5*x+7*11*x+13*x+17+6*x\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr220-8.wat b/benchmarks/pldi2026/crafted/parse_expr220-8.wat new file mode 100644 index 000000000..61f1550c9 --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr220-8.wat @@ -0,0 +1,182 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+10+x+x+3+8\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x+133*11*x+247*x+323+60*x+100*x+140*11*x+260*x+340+3*x+5*x+7*11*x+13*x+17+6*x\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr260-16.wat b/benchmarks/pldi2026/crafted/parse_expr260-16.wat new file mode 100644 index 000000000..22c67a76d --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr260-16.wat @@ -0,0 +1,241 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 7 + i32.add + if + end + local.get 0 + i32.const 8 + i32.add + if + end + local.get 0 + i32.const 9 + i32.add + if + end + local.get 0 + i32.const 10 + i32.add + if + end + local.get 0 + i32.const 11 + i32.add + if + end + local.get 0 + i32.const 12 + i32.add + if + end + local.get 0 + i32.const 13 + i32.add + if + end + local.get 0 + i32.const 14 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x+133*11*x+247*x+323+60*x+100*x+140*11*x+260*x+340+3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x*x*x+25*x+35*11*x+65*x+85+18\00")) diff --git a/benchmarks/pldi2026/crafted/parse_expr260-8.wat b/benchmarks/pldi2026/crafted/parse_expr260-8.wat new file mode 100644 index 000000000..06bde7795 --- /dev/null +++ b/benchmarks/pldi2026/crafted/parse_expr260-8.wat @@ -0,0 +1,181 @@ +(module + (type (;0;) (func (result i32))) + (type (;1;) (func)) + (type (;2;) (func (param i32 i32) (result i32))) + (func (;0;) (type 0) (result i32) + (local i32 i32 i32) + global.get 0 + global.get 1 + i32.add + local.set 0 + local.get 0 + i32.load + i32.const 255 + i32.and) + (func (;1;) (type 1) + global.get 1 + i32.const 1 + i32.add + global.set 1) + (func (;2;) (type 0) (result i32) + (local i32 i32) + i32.const 0 + local.set 0 + loop ;; label = @1 + call 0 + local.tee 1 + i32.const 48 + i32.ge_s + local.get 1 + i32.const 57 + i32.le_s + i32.and + if ;; label = @2 + local.get 0 + i32.const 10 + i32.mul + local.get 1 + i32.const 48 + i32.sub + i32.add + local.set 0 + call 1 + br 1 (;@1;) + end + end + local.get 0) + (func (;3;) (type 0) (result i32) + (local i32) + call 0 + local.tee 0 + i32.const 48 + i32.ge_s + local.get 0 + i32.const 57 + i32.le_s + i32.and + if (result i32) ;; label = @1 + call 2 + else + local.get 0 + i32.const 120 + i32.eq + if (result i32) ;; label = @2 + call 1 + global.get 2 + else + i32.const 0 + end + end) + (func (;4;) (type 0) (result i32) + (local i32 i32 i32) + call 3 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 42 + i32.ne + br_if 1 (;@1;) + call 1 + call 3 + local.set 2 + local.get 0 + local.get 2 + i32.mul + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;5;) (type 0) (result i32) + (local i32 i32 i32) + call 4 + local.set 0 + block ;; label = @1 + loop ;; label = @2 + call 0 + local.tee 1 + i32.const 43 + i32.ne + br_if 1 (;@1;) + call 1 + call 4 + local.set 2 + local.get 0 + local.get 2 + i32.add + local.set 0 + br 0 (;@2;) + end + end + local.get 0) + (func (;6;) (type 2) (param i32 i32) (result i32) + local.get 0 + global.set 2 + local.get 1 + global.set 0 + i32.const 0 + global.set 1 + call 5) + (func (;7;) (result i32) + (local i32) + i32.const 0 + i32.symbolic + i32.const 1024 + call 6 + local.tee 0 + if + end + i32.const 10 ;; x + i32.const 1024 + call 6 + i32.const 0 + i32.symbolic + i32.const 0 + call 6 + local.tee 0 + if + end + local.get 0 + i32.const 1 + i32.add + if + end + local.get 0 + i32.const 2 + i32.add + if + end + local.get 0 + i32.const 3 + i32.add + if + end + local.get 0 + i32.const 4 + i32.add + if + end + local.get 0 + i32.const 5 + i32.add + if + end + local.get 0 + i32.const 6 + i32.add + if + end + ) + (import "console" "assert" (func (param i32))) + (start 7) + (memory (;0;) 1) + (global (;0;) (mut i32) (i32.const 0)) + (global (;1;) (mut i32) (i32.const 0)) + (global (;2;) (mut i32) (i32.const 0)) + (export "memory" (memory 0)) + (export "eval_expr" (func 6)) + (data (i32.const 0) "x+1\00") + (data (;0;) (i32.const 1024) "3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x+25*x*x*x+35*11*x+65*x+85+18*x+30*x+42*11*x+78*x+102+21*x+35*x+49*11*x+91*x+119+24*x+40*x+56*11*x+104*x+136+27*x+45*x+63*11*x+117*x+153+30*x+50*x+70*11*x+130*x+170+33*x+55*x+77*11*x+143*x+187+36*x+60*x+84*11*x+156*x+204+39*x+65*x+91*11*x+169*x+221+42*x+70*x+98*11*x+182*x+238+45*x+75*x+105*11*x+195*x+255+48*x*x*x+80*x+112*11*x+208*x+272+51*x*x*x+85*x+119*11*x+221*x+289+54*x+90*x+126*11*x+234*x+306+57*x*x*x+95*x+133*11*x+247*x+323+60*x+100*x+140*11*x+260*x+340+3*x+5*x+7*11*x+13*x+17+6*x+10*x+14*11*x+26*x+34+9*x+15*x+21*11*x+39*x+51+12*x+20*x+28*11*x+52*x+68+15*x*x*x+25*x+35*11*x+65*x+85+18\00"))